Esempio n. 1
0
void json_send_qstring(const char *s) {
    const char *hex_digits = "0123456789abcdef", *begin = s;
    unsigned int len = 0;
    char escaped[6] = { '\\', 'u', '0', '0', 'x', 'x' };

    CGI_PUTC('"');
    while(1) {
	unsigned char c = begin[len];
	/* flush on end of string and escape quotation mark, reverse solidus,
	 * and the control characters (U+0000 through U+001F) */
	if(c < ' ' || c == '"' || c== '\\') {
	    if(len) /* flush */
		CGI_PUTD(begin, len);
	    begin = &begin[len+1];
	    len = 0;
	    if(!c) {
		CGI_PUTC('"');
		return;
	    }
	    escaped[4] = hex_digits[c >> 4];
	    escaped[5] = hex_digits[c & 0xf];
	    CGI_PUTD(escaped, 6);
	} else
	    len++;
    }
Esempio n. 2
0
void fcgi_send_file_meta(void) {
    const char *metakey;
    const void *metavalue;
    unsigned int created_at;
    sx_hash_t etag;
    int metasize;
    int comma = 0;
    rc_ty s;

    s = sx_hashfs_getfilemeta_begin(hashfs, volume, path, get_arg("rev"), &created_at, &etag);
    if(s != OK)
	quit_errnum(s == ENOENT ? 404 : 500);

    if(is_object_fresh(&etag, 'M', created_at))
	return;

    CGI_PUTS("Content-type: application/json\r\n\r\n{\"fileMeta\":{");
    while((s = sx_hashfs_getfilemeta_next(hashfs, &metakey, &metavalue, &metasize)) == OK) {
	char hexval[SXLIMIT_META_MAX_VALUE_LEN*2+1];
	if(comma)
	    CGI_PUTC(',');
	else
	    comma |= 1;
	json_send_qstring(metakey);
	CGI_PUTS(":\"");
	bin2hex(metavalue, metasize, hexval, sizeof(hexval));
	CGI_PUTS(hexval);
	CGI_PUTC('"');
    }
    CGI_PUTS("}");
    if (s != ITER_NO_MORE)
	quit_itererr("Failed to get file metadata", s);
    CGI_PUTS("}");
}
Esempio n. 3
0
static int hash_presence_callback(const char *hexhash, unsigned int index, int code, void *context)
{
    hash_presence_ctx_t *ctx = (hash_presence_ctx_t*)context;
    sx_hashfs_t *h = ctx->h;
    sx_nodelist_t *nodes;
    sx_hash_t hash;
    if (code != 200) {
	if (code < 0)
	    WARN("Failed to query hash %.*s: %s", 40, hexhash, sx_hashfs_geterrmsg(h));
	if (hex2bin(hexhash, SXI_SHA1_TEXT_LEN, hash.b, sizeof(hash.b))) {
	    WARN("hex2bin failed on %.*s", 40, hexhash);
	    return -1;
	}
	nodes = sx_hashfs_putfile_hashnodes(h, &hash);
	if (!nodes) {
	    WARN("hashnodes failed");
	    return -1;
	}
	if(ctx->comma)
	    CGI_PUTC(',');
	else
	    ctx->comma |= 1;
        DEBUG("Requesting from user: #%.*s#", 40, hexhash);
	send_qstring_hash(&hash);
	CGI_PUTC(':');
	/* Although there is no danger in doing so, nodes SHOULD NOT be randomized:
	 * hdist already does a pretty good job here */
	send_nodes(nodes);
	sx_nodelist_delete(nodes);
    }
    send_keepalive();
    return 0;
}
Esempio n. 4
0
void fcgi_send_file(void) {
    sx_hashfs_file_t filedata;
    const sx_hash_t *hash;
    sx_nodelist_t *nodes;
    sx_hash_t etag;
    int comma = 0;
    rc_ty s = sx_hashfs_getfile_begin(hashfs, volume, path, get_arg("rev"), &filedata, &etag);

    if(s != OK)
	quit_errnum(s == ENOENT ? 404 : 500);

    if(is_object_fresh(&etag, 'F', filedata.created_at)) {
	sx_hashfs_getfile_end(hashfs);
	return;
    }

    CGI_PRINTF("Content-type: application/json\r\n\r\n{\"blockSize\":%d,\"fileSize\":", filedata.block_size);
    CGI_PUTLL(filedata.file_size);
    CGI_PRINTF(",\"createdAt\":%u,\"fileRevision\":\"%s\",\"fileData\":[", filedata.created_at, filedata.revision);

    while((s = sx_hashfs_getfile_block(hashfs, &hash, &nodes)) == OK) {
	if(comma)
	    CGI_PUTC(',');
	else
	    comma |= 1;
	CGI_PUTC('{');
	send_qstring_hash(hash);
	CGI_PUTC(':');
	/* Nodes are in NL_PREVNEXT order and MUST NOT be randomized
	 * (see comments in sx_hashfs_getfile_block) */
	send_nodes(nodes);
	CGI_PUTC('}');

	sx_nodelist_delete(nodes);
    }

    sx_hashfs_getfile_end(hashfs);
    CGI_PUTS("]");
    if(s != ITER_NO_MORE)
	quit_itererr("Failed to list file blocks", s);

    CGI_PUTS("}");
}
Esempio n. 5
0
static void send_error_helper(const char sep, int errnum, const char *message) {
    sx_uuid_t node_uuid;
    CGI_PRINTF("%c\"ErrorMessage\":", sep);
    json_send_qstring(message ? message : "");
    if (errnum == 500 || errnum == 400) {
        if (message)
            WARN("HTTP %d: %s", errnum, message);
        CGI_PUTS(",\"ErrorDetails\":");
        json_send_qstring(msg_log_end());
    }
    CGI_PUTS(",\"NodeId\":");
    json_send_qstring(sx_hashfs_self_uuid(hashfs, &node_uuid)==OK ? node_uuid.string : "<UNKNOWN>");
    CGI_PUTS(",\"ErrorId\":");
    json_send_qstring(msg_get_id());
    CGI_PUTC('}');
}
Esempio n. 6
0
static void send_error_helper(const char sep, int errnum, const char *message) {
    CGI_PRINTF("%c\"ErrorMessage\":", sep);
    json_send_qstring(message);
    if (errnum == 500 || errnum == 400) {
        if (message)
            WARN("HTTP %d: %s", errnum, message);
        CGI_PUTS(",\"ErrorDetails\":");
        json_send_qstring(msg_log_end());
    }
    CGI_PUTS(",\"NodeId\":");
    const sx_node_t *me = sx_hashfs_self(hashfs);
    json_send_qstring(me ? sx_node_uuid(me)->string : "<UNKNOWN>");
    CGI_PUTS(",\"ErrorId\":");
    json_send_qstring(msg_get_id());
    CGI_PUTC('}');
}