Ejemplo n.º 1
0
dstr *dstr_split_len(const char *str, size_t length, const char *sep, size_t seplength, int *count) {
	int slots = 5, i, nelems = 0, start = 0;
	dstr *tokens;

	/* FIXME */
	if (str == NULL || sep == NULL)
		return NULL;
	if (length < 0 || seplength < 1)
		return NULL;
	if ((tokens = ALLOC(slots * sizeof *tokens)) == NULL)
		return NULL;
	if (length == 0) {
		*count = 0;
		return tokens;
	}

	for (i = 0; i < length - seplength + 1; ++i) {
		/* make sure there is room for the next and final ones */
		if (slots < nelems + 2) {
			slots *= 2;
			if (RESIZE(tokens, slots * sizeof *tokens) == NULL)
				goto err;
		}
		if ((seplength == 1 && str[i] == sep[0]) || !memcmp(str + i, sep, seplength)) {
			if ((tokens[nelems] = dstr_new_len(str + start, i - start)) == NULL)
				goto err;
			++nelems;
			start = i + seplength;
			i += seplength - 1;
		}
	}
	/* add the final one */
	if ((tokens[nelems] = dstr_new_len(str + start, length - start)) == NULL)
		goto err;
	++nelems;
	*count = nelems;
	return tokens;

err:
	for (i = 0; i < nelems; ++i)
		dstr_free(tokens[i]);
	FREE(tokens);
	*count = 0;
	return NULL;
}
Ejemplo n.º 2
0
dstr dstr_new(const char *str) {
	size_t length = str ? strlen(str) : 0;

	return dstr_new_len(str, length);
}
Ejemplo n.º 3
0
dstr *dstr_split_args(const char *line, int *argc) {
	const char *p = line;
	dstr current = NULL;
	dstr *argv = NULL;

	*argc = 0;
	for (;;) {
		while (*p && isspace(*p))
			++p;
		if (*p) {
			int inq  = 0; /* 1 if in quotes */
			int insq = 0; /* 1 if in single quotes */
			int done = 0;

			if (current == NULL)
				current = dstr_new_len("", 0);
			while (!done) {
				/* FIXME */
				if (inq) {
					if (*p == '\\' && *(p + 1) == 'x' &&
						is_hex_digit(*(p + 2)) && is_hex_digit(*(p + 3))) {
						unsigned char byte = 16 * hex_digit_to_int(*(p + 2)) +
							hex_digit_to_int(*(p + 3));

						p += 3;
						current = dstr_cat_len(current, (char *)&byte, 1);
					} else if (*p == '\\' && *(p + 1)) {
						char c;

						++p;
						switch (*p) {
						case 'a':
							c = '\a';
							break;
						case 'b':
							c = '\b';
							break;
						case 'n':
							c = '\n';
							break;
						case 'r':
							c = '\r';
							break;
						case 't':
							c = '\t';
							break;
						default:
							c = *p;
							break;
						}
						current = dstr_cat_len(current, &c, 1);
					} else if (*p == '"') {
						/* closing quote must be followed by a space or not at all */
						if (*(p + 1) && !isspace(*(p + 1)))
							goto err;
						done = 1;
					/* unterminated quotes */
					} else if (*p == '\0')
						goto err;
					else
						current = dstr_cat_len(current, p, 1);
				} else if (insq) {
					if (*p == '\\' && *(p + 1) == '\'') {
						++p;
						current = dstr_cat_len(current, "'", 1);
					} else if (*p == '\'') {
						/* closing quote must be followed by a space or not at all */
						if (*(p + 1) && !isspace(*(p + 1)))
							goto err;
						done = 1;
					/* unterminated quotes */
					} else if (*p == '\0')
						goto err;
					else
						current = dstr_cat_len(current, p, 1);
				} else
					switch (*p) {
					case ' ':
					case '\0':
					case '\n':
					case '\r':
					case '\t':
						done = 1;
						break;
					case '"':
						inq = 1;
						break;
					case '\'':
						insq = 1;
						break;
					default:
						current = dstr_cat_len(current, p, 1);
						break;
					}
				if (*p)
					++p;
			}
			if (RESIZE(argv, (*argc + 1) * sizeof (char *)) == NULL)
				goto err;
			argv[*argc] = current;
			++*argc;
			current = NULL;
		} else
			return argv;
	}

err:
	{
		int i;

		for (i = 0; i < *argc; ++i)
			dstr_free(argv[i]);
		FREE(argv);
		if (current)
			dstr_free(current);
		return NULL;
	}
}
Ejemplo n.º 4
0
static int impvbaw_exec(void *data, void *data2) {
	RAII_VAR(struct msg *, msg, (struct msg *)data, msg_decr);
	Quote *quote = (Quote *)msg->data;
	struct msgs *out = (struct msgs *)data2;
	dstr contract;
	float last;
	char *p;
	table_node_t node;

	contract = dstr_new(quote->thyquote.m_cHYDM);
	if (!strcmp(contract, "") || (fabs(quote->thyquote.m_dZXJ) <= 0.000001 &&
		fabs(quote->thyquote.m_dMRJG1) <= 0.000001 &&
		fabs(quote->thyquote.m_dMCJG1) <= 0.000001)) {
		xcb_log(XCB_LOG_WARNING, "Invalid quote: '%d,%d,%s,%.2f,%.2f,%.2f'",
			quote->thyquote.m_nTime,
			quote->m_nMSec,
			contract,
			quote->thyquote.m_dZXJ,
			quote->thyquote.m_dMRJG1,
			quote->thyquote.m_dMCJG1);
		goto end;
	}
	/* FIXME */
	if (!strncasecmp(contract, "IO", 2) || !strncasecmp(contract, "HO", 2) ||
		!strncasecmp(contract, "00", 2) || !strncasecmp(contract, "60", 2))
		goto end;
	last = quote->thyquote.m_dZXJ;
	if ((p = strrchr(contract, 'C')) == NULL)
		p = strrchr(contract, 'P');
	/* FIXME: option quote */
	if (p && p != contract && p != contract + dstr_length(contract) - 1 &&
		((*(p - 1) == '-' && *(p + 1) == '-') || (isdigit(*(p - 1)) && isdigit(*(p + 1))))) {
		dstr spotname, type, strike;
		float spot;
		struct prices *prices;
		double expiry, vol, vol2, vol3;
		struct tm lt;
		char *res;

		spotname = *(p - 1) == '-' ? dstr_new_len(contract, p - contract - 1) :
			dstr_new_len(contract, p - contract);
		type     = dstr_new_len(p, 1);
		strike   = *(p + 1) == '-' ? dstr_new_len(p + 2, contract + dstr_length(contract) - p - 2) :
			dstr_new_len(p + 1, contract + dstr_length(contract) - p - 1);
		table_rwlock_rdlock(spots);
		if ((node = table_find(spots, spotname)) == NULL) {
			table_rwlock_unlock(spots);
			dstr_free(strike);
			dstr_free(type);
			dstr_free(spotname);
			goto end;
		}
		spot = table_node_float(node);
		table_rwlock_unlock(spots);
		if (fabs(spot) <= 0.000001) {
			xcb_log(XCB_LOG_WARNING, "The price of spot '%s' be zero", spotname);
			dstr_free(strike);
			dstr_free(type);
			dstr_free(spotname);
			goto end;
		}
		table_lock(optns);
		if ((node = table_find(optns, contract)) == NULL) {
			if (NEW(prices)) {
				prices->prelast = last;
				prices->prebid1 = quote->thyquote.m_dMRJG1;
				prices->preask1 = quote->thyquote.m_dMCJG1;
				prices->prespot = spot;
				table_insert(optns, dstr_new(contract), prices);
			} else
				xcb_log(XCB_LOG_WARNING, "Error allocating memory for prices");
		} else {
			prices = (struct prices *)table_node_value(node);

			if (fabs(prices->prelast - last) <= 0.000001 &&
				fabs(prices->prebid1 - quote->thyquote.m_dMRJG1) <= 0.000001 &&
				fabs(prices->preask1 - quote->thyquote.m_dMCJG1) <= 0.000001 &&
				fabs(prices->prespot - spot) <= 0.000001) {
				table_unlock(optns);
				dstr_free(strike);
				dstr_free(type);
				dstr_free(spotname);
				goto end;
			} else {
				prices->prelast = last;
				prices->prebid1 = quote->thyquote.m_dMRJG1;
				prices->preask1 = quote->thyquote.m_dMCJG1;
				prices->prespot = spot;
			}
		}
		table_unlock(optns);
		if ((node = table_find(expiries, contract)))
			expiry = table_node_double(node);
		else {
			char *month;
			struct timeval tv;
			int diff;

			xcb_log(XCB_LOG_WARNING, "No exact expiry date for '%s'", contract);
			month = spotname + dstr_length(spotname) - 2;
			gettimeofday(&tv, NULL);
			if ((diff = atoi(month) - localtime_r(&tv.tv_sec, &lt)->tm_mon - 1) < 0)
				diff += 12;
			if (diff == 0)
				diff = 1;
			expiry = diff / 12.0;
		}
		/* FIXME: last price */
		if (fabs(last) <= 0.000001)
			vol = NAN;
		else
			vol = impv_baw(spot, atof(strike), r, r, expiry, last,
				!strcasecmp(type, "C") ? AMER_CALL : AMER_PUT);
		/* FIXME: bid price 1 */
		if (fabs(quote->thyquote.m_dMRJG1) <= 0.000001)
			vol2 = NAN;
		else if (fabs(quote->thyquote.m_dMRJG1 - last) <= 0.000001)
			vol2 = vol;
		else
			vol2 = impv_baw(spot, atof(strike), r, r, expiry, quote->thyquote.m_dMRJG1,
				!strcasecmp(type, "C") ? AMER_CALL : AMER_PUT);
		/* FIXME: ask price 1 */
		if (fabs(quote->thyquote.m_dMCJG1) <= 0.000001)
			vol3 = NAN;
		else if (fabs(quote->thyquote.m_dMCJG1 - last) <= 0.000001)
			vol3 = vol;
		else
			vol3 = impv_baw(spot, atof(strike), r, r, expiry, quote->thyquote.m_dMCJG1,
				!strcasecmp(type, "C") ? AMER_CALL : AMER_PUT);
		if ((res = ALLOC(512))) {
			time_t t = (time_t)quote->thyquote.m_nTime;
			char datestr[64];

			strftime(datestr, sizeof datestr, "%F %T", localtime_r(&t, &lt));
			snprintf(res, 512, "IMPVBAW,%s.%03d,%s|%.2f,%f,%.2f,%f,%.2f,%f,%.2f",
				datestr,
				quote->m_nMSec,
				contract,
				last,
				vol,
				quote->thyquote.m_dMRJG1,
				vol2,
				quote->thyquote.m_dMCJG1,
				vol3,
				spot);
			out2rmp(res);
			snprintf(res, 512, "IMPVBAW,%d,%d,%s,%.2f,%f,%.2f,%f,%.2f,%f,%.2f,%s,%s,%s,%f,%f,%d,0,0",
				quote->thyquote.m_nTime,
				quote->m_nMSec,
				contract,
				last,
				vol,
				quote->thyquote.m_dMRJG1,
				vol2,
				quote->thyquote.m_dMCJG1,
				vol3,
				spot,
				spotname,
				type,
				strike,
				r,
				expiry,
				quote->thyquote.m_nCJSL);
			if (out2msgs(res, out) == -1)
				FREE(res);
		} else
			xcb_log(XCB_LOG_WARNING, "Error allocating memory for result");
		dstr_free(strike);
		dstr_free(type);
		dstr_free(spotname);
	/* future quote */
	} else {
		table_rwlock_wrlock(spots);
		if ((node = table_find(spots, contract)) == NULL) {
			if ((node = table_insert_raw(spots, contract)))
				table_set_float(node, last);
		} else {
			table_set_float(node, last);
			dstr_free(contract);
		}
		table_rwlock_unlock(spots);
		return 0;
	}

end:
	dstr_free(contract);
	return 0;
}
Ejemplo n.º 5
0
static inline void load_config(void) {
	/* FIXME */
	if ((cfg = config_load("/etc/xcb/vxo.conf"))) {
		char *cat = category_browse(cfg, NULL);
		struct variable *var;

		while (cat) {
			if (!strcasecmp(cat, "general")) {
				struct variable *var = variable_browse(cfg, cat);

				while (var) {
					if (!strcasecmp(var->name, "inmsg")) {
						if (strcmp(var->value, ""))
							inmsg = var->value;
					} else
						xcb_log(XCB_LOG_WARNING, "Unknown variable '%s' in "
							"category '%s' of vxo.conf", var->name, cat);
					var = var->next;
				}
			} else if (!strcasecmp(cat, "expiries")) {
				var = variable_browse(cfg, cat);
				while (var) {
					char *p;

					if ((p = strrchr(var->name, 'C')) == NULL)
						p = strrchr(var->name, 'P');
					if (p && p != var->name && p != var->name + strlen(var->name) - 1 &&
						((*(p - 1) == '-' && *(p + 1) == '-') ||
						(isdigit(*(p - 1)) && isdigit(*(p + 1))))) {
						dstr spotname, strike;
						struct pd *pd;
						struct scp *scp;

						spotname = *(p - 1) == '-'
							? dstr_new_len(var->name, p - var->name - 1)
							: dstr_new_len(var->name, p - var->name);
						strike   = *(p + 1) == '-'
							? dstr_new_len(p + 2, var->name + strlen(var->name) - p - 2)
							: dstr_new_len(p + 1, var->name + strlen(var->name) - p - 1);
						if ((pd = table_get_value(spots, spotname)) == NULL) {
							if (NEW(scp)) {
								scp->strike = atof(strike);
								scp->cvol   = scp->pvol  = NAN;
								scp->cvol2  = scp->pvol2 = NAN;
								scp->cvol3  = scp->pvol3 = NAN;
								if (NEW(pd)) {
									pd->prevxo = pd->prevxo2 = pd->prevxo3 = NAN;
									pd->sep    = *(p - 1) == '-' ? "-" : "";
									pd->dlist  = dlist_new(NULL, scpfree);
									dlist_insert_tail(pd->dlist, scp);
									table_insert(spots, spotname, pd);
								} else
									FREE(scp);
							} else
								dstr_free(spotname);
						} else {
							dlist_iter_t iter = dlist_iter_new(pd->dlist, DLIST_START_HEAD);
							dlist_node_t node;

							while ((node = dlist_next(iter))) {
								scp = (struct scp *)dlist_node_value(node);
								if (scp->strike > atof(strike) ||
									fabs(scp->strike - atof(strike)) <= 0.000001)
									break;
							}
							dlist_iter_free(&iter);
							if (node == NULL || scp->strike > atof(strike)) {
								if (NEW(scp)) {
									scp->strike = atof(strike);
									scp->cvol   = scp->pvol  = NAN;
									scp->cvol2  = scp->pvol2 = NAN;
									scp->cvol3  = scp->pvol3 = NAN;
								}
								if (node == NULL)
									dlist_insert_tail(pd->dlist, scp);
								else
									dlist_insert(pd->dlist, node, scp, 0);
							}
							dstr_free(spotname);
						}
						dstr_free(strike);
					}
					var = var->next;
				}
			}
			cat = category_browse(cfg, cat);
		}
	}
}