diff src/c/lacweb.c @ 167:2be573fec9a6

Unurlifying a datatype; longjmp-based error signaling mechanism
author Adam Chlipala <adamc@hcoop.net>
date Tue, 29 Jul 2008 15:25:42 -0400
parents f0d3402184d1
children 2232ab355f66
line wrap: on
line diff
--- a/src/c/lacweb.c	Tue Jul 29 14:28:44 2008 -0400
+++ b/src/c/lacweb.c	Tue Jul 29 15:25:42 2008 -0400
@@ -3,15 +3,24 @@
 #include <string.h>
 #include <ctype.h>
 #include <assert.h>
+#include <setjmp.h>
+#include <stdarg.h>
 
 #include "types.h"
 
 lw_unit lw_unit_v = {};
 
+#define ERROR_BUF_LEN 1024
+
 struct lw_context {
   char *page, *page_front, *page_back;
   char *heap, *heap_front, *heap_back;
   char **inputs;
+
+  jmp_buf jmp_buf;
+
+  failure_kind failure_kind;
+  char error_message[ERROR_BUF_LEN];
 };
 
 extern int lw_inputs_len;
@@ -27,6 +36,9 @@
 
   ctx->inputs = calloc(lw_inputs_len, sizeof(char *));
 
+  ctx->failure_kind = SUCCESS;
+  ctx->error_message[0] = 0;
+
   return ctx;
 }
 
@@ -37,12 +49,49 @@
   free(ctx);
 }
 
-void lw_reset(lw_context ctx) {
+void lw_reset_keep_request(lw_context ctx) {
   ctx->page_front = ctx->page;
   ctx->heap_front = ctx->heap;
+
+  ctx->failure_kind = SUCCESS;
+  ctx->error_message[0] = 0;
+}
+
+void lw_reset_keep_error_message(lw_context ctx) {
+  ctx->page_front = ctx->page;
+  ctx->heap_front = ctx->heap;
+
+  ctx->failure_kind = SUCCESS;
+}
+
+void lw_reset(lw_context ctx) {
+  lw_reset_keep_request(ctx);
   memset(ctx->inputs, 0, lw_inputs_len * sizeof(char *));
 }
 
+void lw_handle(lw_context, char *);
+
+failure_kind lw_begin(lw_context ctx, char *path) {
+  if (!setjmp(ctx->jmp_buf))
+    lw_handle(ctx, path);
+
+  return ctx->failure_kind;
+}
+
+void lw_error(lw_context ctx, failure_kind fk, const char *fmt, ...) {
+  va_list ap;
+  va_start(ap, fmt);
+
+  ctx->failure_kind = fk;
+  vsnprintf(ctx->error_message, ERROR_BUF_LEN, fmt, ap);
+
+  longjmp(ctx->jmp_buf, 1);
+}
+
+char *lw_error_message(lw_context ctx) {
+  return ctx->error_message;
+}
+
 int lw_input_num(char*);
 
 void lw_set_input(lw_context ctx, char *name, char *value) {