Example #1
0
static int brigade_putc(lua_State*L)
{
	apr_bucket_brigade *bb = (apr_bucket_brigade *) CHECK_BUCKETBRIGADE_OBJECT(1);
	const char c = (const char)luaL_checkint(L,2);

	apr_status_t rc = apr_brigade_putc(bb, NULL,NULL, c);
	lua_pushinteger(L,rc);
	return 1;
}
static apr_status_t upload_filter(ap_filter_t *f, apr_bucket_brigade *bbout,
	ap_input_mode_t mode, apr_read_type_e block, apr_off_t nbytes) {

  char* buf = 0 ;
  char* p = buf ;
  char* e ;
 
  int ret = APR_SUCCESS ;
 
  apr_size_t bytes = 0 ;
  apr_bucket* b ;
  apr_bucket_brigade* bbin ;
 
  upload_ctx* ctx = (upload_ctx*) f->ctx ;
  if ( ctx->parse_state == p_done ) {
    // send an EOS
    APR_BRIGADE_INSERT_TAIL(bbout, apr_bucket_eos_create(bbout->bucket_alloc) ) ;
    return APR_SUCCESS ;
  }

  /* should be more efficient to do this in-place without resorting
   * to a new brigade
   */
  bbin = apr_brigade_create(f->r->pool, f->r->connection->bucket_alloc) ;

  if ( ret = ap_get_brigade(f->next, bbin, mode, block, nbytes) ,
	ret != APR_SUCCESS )
     return ret ;


  for ( b = APR_BRIGADE_FIRST(bbin) ;
	b != APR_BRIGADE_SENTINEL(bbin) ;
	b = APR_BUCKET_NEXT(b) ) {
    const char* ptr = buf ;
    if ( APR_BUCKET_IS_EOS(b) ) {
      ctx->parse_state = p_done ;
      APR_BRIGADE_INSERT_TAIL(bbout,
	 apr_bucket_eos_create(bbout->bucket_alloc) ) ;
      apr_brigade_destroy(bbin) ;
      return APR_SUCCESS ;
    } else if ( apr_bucket_read(b, &ptr, &bytes, APR_BLOCK_READ)
		== APR_SUCCESS ) {
      const char* p = ptr ;
      while ( e = strchr(p, '\n'), ( e && ( e < (ptr+bytes) ) ) ) {
	const char* ptmp = p ;
	*e = 0 ;
	if ( ctx->leftover ) {
		// this'll be grossly inefficient if we get lots of
		// little buckets (we don't in my setup:-)
	  ptmp = apr_pstrcat(f->r->pool, ctx->leftover, p, NULL) ;
	  ctx->leftover = 0 ;
	}
	switch ( ctx->parse_state ) {
	  case p_none:
	    if ( is_boundary(ctx, ptmp) == boundary_part )
	      ctx->parse_state = p_head ;
	    break ;
	  case p_head:
	    if ( (! *ptmp) || ( *ptmp == '\r') )
	      ctx->parse_state = p_field ;
	    else
	      set_header(ctx, ptmp) ;
	    break ;
	  case p_field:
	    switch ( is_boundary(ctx, ptmp) ) {
	      case boundary_part:
		end_body(ctx) ;
		ctx->parse_state = p_head ;
		break ;
	      case boundary_end:
		end_body(ctx) ;
		ctx->parse_state = p_end ;
		break ;
	      case boundary_none:
		if ( ctx->is_file ) {
		  apr_brigade_puts(bbout, ap_filter_flush, f, ptmp) ;
		  apr_brigade_putc(bbout, ap_filter_flush, f, '\n') ;
		} else
		  set_body(ctx, ptmp) ;
		break ;
	    }
	    break ;
	  case p_end:
	    //APR_BRIGADE_INSERT_TAIL(bbout,
	//	apr_bucket_eos_create(bbout->bucket_alloc) ) ;
	    ctx->parse_state = p_done ;
	  case p_done:
	    break ;
	}
	if ( e - ptr >= bytes )
	  break ;
	p = e + 1 ;
      }
      if ( ( ctx->parse_state != p_end ) && ( ctx->parse_state != p_done ) ) {
	size_t bleft = bytes - (p-ptr) ;
	ctx->leftover = apr_pstrndup(f->r->pool, p, bleft ) ;
#ifdef DEBUG
  ap_log_rerror(APLOG_MARK,APLOG_DEBUG,0, f->r, "leftover %d bytes\n\t%s\n\t%s\n", bleft, ctx->leftover, p) ;
#endif
      }
    }
  }
  apr_brigade_destroy(bbin) ;
  return ret ;
}