/* internal (non-inline) part of etna_reserve * - commit current command buffer (if there is a current command buffer) * - signify when current command buffer becomes available using a signal * - switch to next command buffer */ int _etna_reserve_internal(struct etna_ctx *ctx, size_t n) { int status; #ifdef DEBUG fprintf(stderr, "Buffer full\n"); #endif if((ctx->offset*4 + END_COMMIT_CLEARANCE) > COMMAND_BUFFER_SIZE) { fprintf(stderr, "%s: Command buffer overflow! This is likely a programming error in the GPU driver.\n", __func__); abort(); } #ifdef GCABI_HAS_CONTEXT if(ctx->cur_buf == ETNA_CTX_BUFFER) { fprintf(stderr, "%s: Context buffer overflow! This is likely a programming error in the GPU driver.\n", __func__); abort(); } #endif if(ctx->cur_buf != ETNA_NO_BUFFER) { #if 0 fprintf(stderr, "Submitting old buffer %i\n", ctx->cur_buf); #endif /* Queue signal to signify when buffer is available again */ if((status = etna_queue_signal(ctx->queue, ctx->cmdbufi[ctx->cur_buf].sig_id, VIV_WHERE_COMMAND)) != ETNA_OK) { fprintf(stderr, "%s: queue signal for old buffer failed: %i\n", __func__, status); abort(); /* buffer is in invalid state XXX need some kind of recovery */ } /* Otherwise, if there is something to be committed left in the current command buffer, commit it */ if((status = etna_flush(ctx, NULL)) != ETNA_OK) { fprintf(stderr, "%s: reserve failed: %i\n", __func__, status); abort(); /* buffer is in invalid state XXX need some kind of recovery */ } } /* Move on to next buffer if not enough free in current one */ if((status = switch_next_buffer(ctx)) != ETNA_OK) { fprintf(stderr, "%s: can't switch to next command buffer: %i\n", __func__, status); abort(); /* Buffer is in invalid state XXX need some kind of recovery. This could involve waiting and re-uploading the context state. */ } return status; }
/* internal (non-inline) part of etna_reserve * - commit current command buffer (if there is a current command buffer) * - signify when current command buffer becomes available using a signal * - switch to next command buffer */ int _etna_reserve_internal(etna_ctx *ctx, size_t n) { int status; #ifdef DEBUG printf("Buffer full\n"); #endif if(ctx->cur_buf != -1) { /* Otherwise, if there is something to be committed left in the current command buffer, commit it */ if((status = etna_flush(ctx)) != ETNA_OK) return status; /* Queue signal to signify when buffer is available again */ if(viv_event_queue_signal(ctx->cmdbuf_sig[ctx->cur_buf], gcvKERNEL_COMMAND) != 0) return ETNA_INTERNAL_ERROR; } /* Move on to next buffer if not enough free in current one */ status = switch_next_buffer(ctx); return status; }