render_multi.c
changeset 18 86f2e5b7191b
parent 17 8e8b56b0e0f5
child 19 d18606bb6f20
--- a/render_multi.c	Mon Jun 09 03:15:34 2008 +0300
+++ b/render_multi.c	Mon Jun 09 18:58:39 2008 +0300
@@ -53,7 +53,7 @@
         // how many bytes we have already written into the current row
         size_t col;
 
-        // _render_multi_done called for this?
+        // passed in the last segment of data?
         int render_done;
         
         // a pointer to ourself
@@ -79,8 +79,8 @@
     // the render_slices thing
     struct render_slices slices;
 
-    // has render_png_done returned?
-    int png_done;
+    // has render_slices_done returned?
+    int slices_done;
 
     // buffer render_png output in this
     struct evbuffer *out_buf;
@@ -154,10 +154,9 @@
         ctx->cb_data(ctx->out_buf, ctx->cb_arg);
     
     // was that the last piece of PNG data?
-    if (ctx->png_done && evbuffer_get_length(ctx->out_buf) == 0) {
+    if (ctx->slices_done && evbuffer_get_length(ctx->out_buf) == 0) {
         // PNG data done!
         _render_multi_do_png_done(ctx);
-
     }
 }
 
@@ -188,21 +187,23 @@
         assert(ctx->nodes[i].render_remote == NULL);
         assert(ctx->nodes[i].col == 0);
     }
+    
+    // finish off the render_slices
+    if (render_slices_done(&ctx->slices))
+        ERROR("render_slices_done");
+    
+    // mark this as complete, all data is now in the out buffer
+    ctx->slices_done = 1;
 
-    // and that the PNG stuff is complete
-    assert(ctx->png_done);
-    
     // if that all the data handled now, we're done
     _render_multi_do_png_data(ctx);
 
     // don't free ourself, our user does that (probably already did, via render_png_done)
     return;
 
-/*
 error:    
-    / * render_png_done failed, probably because we didn't have enough data * /
+    /* render_slices_done -> render_png_done failed, probably because we didn't have enough data */
     _render_multi_do_fail(ctx, FAIL_PARTIAL);
-*/    
 }
 
 // the request completed abnormally. Flags:
@@ -301,17 +302,12 @@
             ERROR("read");
 
     } else if (ret == 0) {
-        // mark it as done
-        ctx->render_done = 1;
-        ctx->self->renders_done++;
-       
         // this ctx's remote render is done
         render_remote_done(ctx->render_remote);
         ctx->render_remote = NULL;
 
-        // we should only receive an EOF when ctx->col is zero or full
-        if (ctx->col != 0 || ctx->col != ctx->slice_width)
-            ERROR("incomplete data for slice %zu: %zu/%zu bytes", ctx->info->index, ctx->col, ctx->slice_width);
+        // count how many are done
+        ctx->self->renders_done++;
 
         // are all of them done?
         if (ctx->self->renders_done == ctx->self->node_count) {
@@ -324,44 +320,43 @@
         return;
     }
 
-    // check if we were expecting
-    
     // ok, we received some data normally
     ctx->col += ret;
 
-    // is our slice full now?
+    // is this segment full now?
     if (ctx->col == ctx->slice_width) {
-        // yes!
         int status;
         
+        // pass the segment in to render_slices
         if ((status = render_slices_segment_done(&ctx->self->slices, ctx->info->index)) == -1)
             ERROR("render_slices_segment_done");
-        
+
+        // reset the col marker
+        ctx->col = 0;
+
         // row done?
         if (status & SLICE_PROCESS_ROW) {
-            // XXX: ignore SLICE_PROCESS_ROW from render_slices_process_row
+            // process the row via render_slices
             status = render_slices_process_row(&ctx->self->slices);
-
-            // we should have SLICE_CONTINUE by now, unless the PNG is done
-            if (status & SLICE_CONTINUE) {
-                // clear the col values and reschedule the reads in case they were ~SLICE_CONTINUE
-                int i;
-                for (i = 0; i < ctx->self->node_count; i++) {
-                    ctx->self->nodes[i].col = 0;
-                    render_remote_reschedule(ctx->self->nodes[i].render_remote);
-                }
-            } else {
-                // XXX: assume render_slices_process_row doesn't return a SLICE_PROCESS_ROW alone
-                assert(status == 0);
-
-                ctx->self->png_done = 1;
-
-                // and wait for the EOF...
-            }
+            
         }
 
-        // if we got SLICE_CONTINUE here, I don't care, don't try and get another row now
-        // just fall through and reschedule
+        // do we need to continue?
+        if (status & SLICE_CONTINUE) {
+            // reschedule the reads in case they were ~SLICE_CONTINUE
+            int i;
+
+            for (i = 0; i < ctx->self->node_count; i++) {
+                // just don't reschedule those that are already EOF...
+                if (ctx->self->nodes[i].render_remote)
+                    render_remote_reschedule(ctx->self->nodes[i].render_remote);
+            }
+
+        } else {
+            // don't read any more data yet, we'll be rescheduled by someone else
+            return;
+
+        }
     }
 
     // ok, reschedule ourselves