void glxx_buffer_subdata(GLXX_BUFFER_T *buffer, int32_t offset, int32_t size, const void *data)
{
   vcos_assert(offset >= 0 && size >= 0);
   vcos_assert(data);

   //if write_would_block(buffer->pool[buffer->current_item] 
   //we pick one of the other pool items, copy the entirety of the current item
   //into that item, and then the new subdata

   if(write_would_block(&buffer->pool[buffer->current_item]))
   {
      //pick a non busy entry from the pool;
      uint32_t i;
      for(i = 0; i< GLXX_BUFFER_POOL_SIZE; i++)
      {
         if(i!=(uint32_t)buffer->current_item && !write_would_block(&buffer->pool[i]))
               break;
      }
      if(i<GLXX_BUFFER_POOL_SIZE)
      {  //found one
         //copy existing data into this new item assuming alloc succeeds
         uint32_t existing_size = mem_get_size(buffer->pool[buffer->current_item].mh_storage);
         bool ok;
         void * existing_data = mem_lock(buffer->pool[buffer->current_item].mh_storage);
         ok = glxx_buffer_inner_data(&buffer->pool[i],existing_size,existing_data,true);
         mem_unlock(buffer->pool[buffer->current_item].mh_storage);
         if(ok)
         {
#ifdef __VIDEOCORE4__
            //unretain current one, so when fixer also unretains, retain count will fall to 0
            mem_unretain(buffer->pool[buffer->current_item].mh_storage);
            //retain new one
            if(buffer->pool[i].mh_storage!=MEM_ZERO_SIZE_HANDLE)
               mem_retain(buffer->pool[i].mh_storage);
#endif
            buffer->current_item = i;
         }
      } //else stick with the existing and wait

   }

   glxx_buffer_inner_subdata(&buffer->pool[buffer->current_item],offset,size,data);

#ifdef REQUIRE_MAX_INDEX_CHECK
   buffer->size_used_for_max = 0;
#endif
}
Example #2
0
static VALUE
ossl_ssl_read_internal(int argc, VALUE *argv, VALUE self, int nonblock)
{
    SSL *ssl;
    int ilen, nread = 0;
    VALUE len, str;
    rb_io_t *fptr;

    rb_scan_args(argc, argv, "11", &len, &str);
    ilen = NUM2INT(len);
    if(NIL_P(str)) str = rb_str_new(0, ilen);
    else{
        StringValue(str);
        rb_str_modify(str);
        rb_str_resize(str, ilen);
    }
    if(ilen == 0) return str;

    Data_Get_Struct(self, SSL, ssl);
    GetOpenFile(ossl_ssl_get_io(self), fptr);
    if (ssl) {
	if(!nonblock && SSL_pending(ssl) <= 0)
	    rb_thread_wait_fd(FPTR_TO_FD(fptr));
	for (;;){
	    nread = SSL_read(ssl, RSTRING_PTR(str), RSTRING_LEN(str));
	    switch(ssl_get_error(ssl, nread)){
	    case SSL_ERROR_NONE:
		goto end;
	    case SSL_ERROR_ZERO_RETURN:
		rb_eof_error();
	    case SSL_ERROR_WANT_WRITE:
                write_would_block(nonblock);
                rb_io_wait_writable(FPTR_TO_FD(fptr));
                continue;
	    case SSL_ERROR_WANT_READ:
                read_would_block(nonblock);
                rb_io_wait_readable(FPTR_TO_FD(fptr));
		continue;
	    case SSL_ERROR_SYSCALL:
		if(ERR_peek_error() == 0 && nread == 0) rb_eof_error();
		rb_sys_fail(0);
	    default:
		ossl_raise(eSSLError, "SSL_read:");
	    }
        }
    }
    else {
        ID meth = nonblock ? rb_intern("read_nonblock") : rb_intern("sysread");
        rb_warning("SSL session is not started yet.");
        return rb_funcall(ossl_ssl_get_io(self), meth, 2, len, str);
    }

  end:
    rb_str_set_len(str, nread);
    OBJ_TAINT(str);

    return str;
}
bool glxx_buffer_data(GLXX_BUFFER_T *buffer, int32_t size, const void *data, GLenum usage)
{
   vcos_assert(size >= 0);

   if(write_would_block(&buffer->pool[buffer->current_item]))
   {
      //pick a non busy entry from the pool;
      uint32_t i;
      for(i = 0; i< GLXX_BUFFER_POOL_SIZE; i++)
      {
         if(i!=(uint32_t)buffer->current_item && !write_would_block(&buffer->pool[i]))
            break;
      }
      if(i<GLXX_BUFFER_POOL_SIZE)
      {  //found one
#ifdef __VIDEOCORE4__
         //unretain current one, so when fixer also unretains, retain count will fall to 0
         mem_unretain(buffer->pool[buffer->current_item].mh_storage);
         //retain new one
         if(buffer->pool[i].mh_storage!=MEM_ZERO_SIZE_HANDLE)
            mem_retain(buffer->pool[i].mh_storage);
#endif
         buffer->current_item = i;

      } //else stick with the existing and wait
   }

   if(!glxx_buffer_inner_data(&buffer->pool[buffer->current_item],size,data,false))
      return false;

   //successfuly allocated memory and copied data
   buffer->usage = usage;

#ifdef REQUIRE_MAX_INDEX_CHECK
   buffer->size_used_for_max = 0;
#endif

   return true;
}
Example #4
0
static VALUE
ossl_ssl_write_internal(VALUE self, VALUE str, int nonblock)
{
    SSL *ssl;
    int nwrite = 0;
    rb_io_t *fptr;

    StringValue(str);
    Data_Get_Struct(self, SSL, ssl);
    GetOpenFile(ossl_ssl_get_io(self), fptr);

    if (ssl) {
	for (;;){
	    nwrite = SSL_write(ssl, RSTRING_PTR(str), RSTRING_LEN(str));
	    switch(ssl_get_error(ssl, nwrite)){
	    case SSL_ERROR_NONE:
		goto end;
	    case SSL_ERROR_WANT_WRITE:
                write_would_block(nonblock);
                rb_io_wait_writable(FPTR_TO_FD(fptr));
                continue;
	    case SSL_ERROR_WANT_READ:
                read_would_block(nonblock);
                rb_io_wait_readable(FPTR_TO_FD(fptr));
                continue;
	    case SSL_ERROR_SYSCALL:
		if (errno) rb_sys_fail(0);
	    default:
		ossl_raise(eSSLError, "SSL_write:");
	    }
        }
    }
    else {
        ID id_syswrite = rb_intern("syswrite");
        rb_warning("SSL session is not started yet.");
	return rb_funcall(ossl_ssl_get_io(self), id_syswrite, 1, str);
    }

  end:
    return INT2NUM(nwrite);
}
Example #5
0
static VALUE
ossl_start_ssl(VALUE self, int (*func)(), const char *funcname, int nonblock)
{
    SSL *ssl;
    rb_io_t *fptr;
    int ret, ret2;
    VALUE cb_state;

    rb_ivar_set(self, ID_callback_state, Qnil);

    Data_Get_Struct(self, SSL, ssl);
    GetOpenFile(ossl_ssl_get_io(self), fptr);
    for(;;){
	ret = func(ssl);

        cb_state = rb_ivar_get(self, ID_callback_state);
        if (!NIL_P(cb_state))
            rb_jump_tag(NUM2INT(cb_state));

	if (ret > 0)
	    break;

	switch((ret2 = ssl_get_error(ssl, ret))){
	case SSL_ERROR_WANT_WRITE:
            write_would_block(nonblock);
            rb_io_wait_writable(FPTR_TO_FD(fptr));
            continue;
	case SSL_ERROR_WANT_READ:
            read_would_block(nonblock);
            rb_io_wait_readable(FPTR_TO_FD(fptr));
            continue;
	case SSL_ERROR_SYSCALL:
	    if (errno) rb_sys_fail(funcname);
	    ossl_raise(eSSLError, "%s SYSCALL returned=%d errno=%d state=%s", funcname, ret2, errno, SSL_state_string_long(ssl));
	default:
	    ossl_raise(eSSLError, "%s returned=%d errno=%d state=%s", funcname, ret2, errno, SSL_state_string_long(ssl));
	}
    }

    return self;
}