#include "common.h"#include "keys.h"#include "kxTok.h"Include dependency graph for keys.c:

Go to the source code of this file.
Data Structures | |
| struct | kvt |
| struct | exp |
Enumerations | |
| enum | keyExpType { kxMatch, kxWildMatch, kxGT, kxGE, kxLT, kxLE, kxAnd, kxOr, kxNot, kxXor } |
Functions | |
| kvt * | newKvt (int size) |
| void | freeKvt (struct kvt **pKvt) |
| void | kvtClear (struct kvt *kvt) |
| keyVal * | kvtAdd (struct kvt *kvt, char *key, char *val) |
| void | kvtParseAdd (struct kvt *kvt, char *text) |
| keyVal * | kvtGet (struct kvt *kvt, char *key) |
| char * | kvtLookup (struct kvt *kvt, char *key) |
| void | kvtWriteAll (struct kvt *kvt, FILE *f, struct slName *hideList) |
| static void | getIntVals (struct kvt *kvt, struct exp *exp, int *retLeft, int *retRight) |
| static boolean | rkeyEval (struct kvt *kvt, struct exp *exp) |
| boolean | keyExpEval (struct keyExp *keyExp, struct kvt *kvt) |
| static void | advanceToken () |
| static struct exp * | nextExp () |
| static struct exp * | parseRelation () |
| static struct exp * | parseParenthesized () |
| static struct exp * | parseNot () |
| static struct exp * | parseAndExp () |
| static struct exp * | parseOrExp () |
| static struct exp * | parseExp (struct kxTok *tokList) |
| keyExp * | keyExpParse (char *text) |
| boolean | keyTextScan (char *text, char *key, char *valBuf, int valBufSize) |
Variables | |
| static char const | rcsid [] = "$Id: keys.c,v 1.10 2005/04/10 14:41:23 markd Exp $" |
| static struct kxTok * | token |
| enum keyExpType |
| static void advanceToken | ( | ) | [static] |
Definition at line 331 of file keys.c.
References kxTok::next, and token.
Referenced by parseAndExp(), parseNot(), parseOrExp(), parseParenthesized(), and parseRelation().
Here is the caller graph for this function:

| void freeKvt | ( | struct kvt ** | pKvt | ) |
| static void getIntVals | ( | struct kvt * | kvt, | |
| struct exp * | exp, | |||
| int * | retLeft, | |||
| int * | retRight | |||
| ) | [static] |
Definition at line 152 of file keys.c.
References kvtLookup(), exp::left, and exp::right.
Referenced by rkeyEval().
00155 { 00156 char *rightString = exp->right; 00157 char *leftKey = exp->left; 00158 char *leftString = kvtLookup(kvt, leftKey); 00159 00160 if (leftString == NULL) 00161 *retLeft = 0; 00162 else 00163 *retLeft = atoi(leftString); 00164 if (rightString == NULL) 00165 *retRight = 0; 00166 else 00167 *retRight = atoi(rightString); 00168 }
Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 321 of file keys.c.
References rkeyEval(), and keyExp::rootExp.
Here is the call graph for this function:

| struct keyExp* keyExpParse | ( | char * | text | ) | [read] |
Definition at line 519 of file keys.c.
References AllocVar, kxTokenize(), parseExp(), keyExp::rootExp, tok, keyExp::tokenList, and TRUE.
00522 { 00523 struct keyExp *ke; 00524 struct kxTok *tok; 00525 AllocVar(ke); 00526 ke->tokenList = tok = kxTokenize(text, TRUE); 00527 ke->rootExp = parseExp(tok); 00528 00529 return ke; 00530 }
Here is the call graph for this function:

| boolean keyTextScan | ( | char * | text, | |
| char * | key, | |||
| char * | valBuf, | |||
| int | valBufSize | |||
| ) |
Definition at line 534 of file keys.c.
00536 { 00537 int keySize = strlen(key); 00538 char *s, *nl; 00539 boolean ok = FALSE; 00540 00541 for (s = text; !isspace(s[0]); s = nl+1) 00542 { 00543 nl = strchr(s, '\n'); 00544 assert(nl != NULL); 00545 if (s[keySize] == ' ' && memcmp(s, key, keySize) == 0) 00546 { 00547 char *val = s + keySize + 1; 00548 int valSize = nl - val; 00549 if (valSize >= valBufSize) 00550 valSize = valBufSize-1; 00551 memcpy(valBuf, val, valSize); 00552 valBuf[valSize] = 0; 00553 ok = TRUE; 00554 break; 00555 } 00556 } 00557 return ok; 00558 }
Definition at line 49 of file keys.c.
References kvt::alloced, errAbort(), keyVal::key, kvt::table, kvt::used, and keyVal::val.
Referenced by kvtParseAdd().
00051 { 00052 struct keyVal *kv; 00053 if (kvt->used == kvt->alloced) 00054 errAbort("Too many keys in keyVal(%s %s)", key, val); 00055 kv = &kvt->table[kvt->used++]; 00056 kv->key = key; 00057 kv->val = val; 00058 return kv; 00059 }
Here is the call graph for this function:

Here is the caller graph for this function:

| void kvtClear | ( | struct kvt * | kvt | ) |
Definition at line 85 of file keys.c.
References sameString, kvt::table, and kvt::used.
Referenced by kvtLookup().
00087 { 00088 int i; 00089 struct keyVal *keyTable = kvt->table; 00090 int keysUsed = kvt->used; 00091 00092 for (i=0; i<keysUsed; ++i) 00093 { 00094 if (sameString(key, keyTable[i].key)) 00095 return &keyTable[i]; 00096 } 00097 return NULL; 00098 }
Here is the caller graph for this function:

| char* kvtLookup | ( | struct kvt * | kvt, | |
| char * | key | |||
| ) |
Definition at line 100 of file keys.c.
References kvtGet(), and keyVal::val.
Referenced by getIntVals(), and rkeyEval().
00103 { 00104 struct keyVal *keyVal = kvtGet(kvt, key); 00105 if (keyVal == NULL) 00106 return NULL; 00107 else 00108 return keyVal->val; 00109 }
Here is the call graph for this function:

Here is the caller graph for this function:

| void kvtParseAdd | ( | struct kvt * | kvt, | |
| char * | text | |||
| ) |
Definition at line 61 of file keys.c.
References ArraySize, chopString(), and kvtAdd().
00062 : 00063 * key val 00064 * for each line of text. Text gets many of it's 00065 * space characters and newlines replaced by 0's 00066 * and should persist until call to keysClear(). */ 00067 { 00068 char *lines[256]; 00069 int lineCount; 00070 int i; 00071 char *k, *v; 00072 00073 lineCount = chopString(text, "\n\r", lines, ArraySize(lines)); 00074 for (i=0; i<lineCount; ++i) 00075 { 00076 k = lines[i]; 00077 if ((v = strchr(k, ' ')) != NULL) 00078 { 00079 *v++ = 0; 00080 kvtAdd(kvt, k, v); 00081 } 00082 } 00083 }
Here is the call graph for this function:

Definition at line 111 of file keys.c.
References keyVal::key, mustWrite(), slNameInList(), kvt::table, kvt::used, and keyVal::val.
00113 { 00114 int i; 00115 static char lf = '\n'; 00116 struct keyVal *kv = kvt->table; 00117 int keyCount = kvt->used; 00118 00119 for (i=0; i<keyCount; ++i) 00120 { 00121 char *key = kv->key; 00122 if (kv->val != NULL && !slNameInList(hideList, key)) 00123 fprintf(f, "%s %s\n", key, kv->val); 00124 ++kv; 00125 } 00126 mustWrite(f, &lf, 1); /* Instead of fputc for error checking. */ 00127 }
Here is the call graph for this function:

| struct kvt* newKvt | ( | int | size | ) | [read] |
Definition at line 21 of file keys.c.
References kvt::alloced, AllocVar, needMem(), and kvt::table.
00023 { 00024 struct kvt *kvt; 00025 AllocVar(kvt); 00026 kvt->alloced = size; 00027 kvt->table = needMem(size * sizeof(kvt->table[0])); 00028 return kvt; 00029 }
Here is the call graph for this function:

| static struct exp * nextExp | ( | ) | [static, read] |
Definition at line 500 of file keys.c.
References parseOrExp().
Referenced by parseAndExp(), parseExp(), parseNot(), parseOrExp(), and parseParenthesized().
00502 { 00503 return parseOrExp(); 00504 }
Here is the call graph for this function:

Here is the caller graph for this function:

| static struct exp* parseAndExp | ( | ) | [static, read] |
Definition at line 439 of file keys.c.
References advanceToken(), AllocVar, errAbort(), kxAnd, kxtAnd, exp::left, nextExp(), parseNot(), exp::right, kxTok::string, tok, token, exp::type, and kxTok::type.
Referenced by parseOrExp().
00441 { 00442 struct exp *left; 00443 struct exp *right, *exp; 00444 struct kxTok *tok; 00445 enum kxTokType type; 00446 00447 if ((left = parseNot()) == NULL) 00448 return NULL; 00449 if ((tok = token) == NULL) 00450 return left; 00451 type = token->type; 00452 if (type == kxtAnd) 00453 { 00454 advanceToken(); 00455 right = nextExp(); 00456 if (right == NULL) 00457 errAbort("Expecting expression on the other side of %s", tok->string); 00458 AllocVar(exp); 00459 exp->left = left; 00460 exp->right = right; 00461 exp->type = kxAnd; 00462 return exp; 00463 } 00464 else 00465 return left; 00466 }
Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 506 of file keys.c.
References errAbort(), kxtEnd, nextExp(), token, and kxTok::type.
Referenced by keyExpParse().
00508 { 00509 struct exp *exp; 00510 token = tokList; 00511 exp = nextExp(); 00512 if (token->type != kxtEnd) 00513 { 00514 errAbort("Extra tokens past end of expression. Missing &?"); 00515 } 00516 return exp; 00517 }
Here is the call graph for this function:

Here is the caller graph for this function:

| static struct exp* parseNot | ( | ) | [static, read] |
Definition at line 418 of file keys.c.
References advanceToken(), AllocVar, kxNot, kxtNot, nextExp(), parseParenthesized(), exp::right, token, exp::type, and kxTok::type.
Referenced by parseAndExp().
00420 { 00421 struct exp *exp; 00422 struct exp *right; 00423 00424 if (token == NULL) 00425 return NULL; 00426 if (token->type == kxtNot) 00427 { 00428 advanceToken(); 00429 right = nextExp(); 00430 AllocVar(exp); 00431 exp->right = right; 00432 exp->type = kxNot; 00433 return exp; 00434 } 00435 else 00436 return parseParenthesized(); 00437 }
Here is the call graph for this function:

Here is the caller graph for this function:

| static struct exp* parseOrExp | ( | ) | [static, read] |
Definition at line 468 of file keys.c.
References advanceToken(), AllocVar, errAbort(), kxOr, kxtOr, kxtXor, kxXor, exp::left, nextExp(), parseAndExp(), exp::right, kxTok::string, tok, token, exp::type, and kxTok::type.
Referenced by nextExp().
00470 { 00471 struct exp *left; 00472 struct exp *right, *exp; 00473 struct kxTok *tok; 00474 enum kxTokType type; 00475 00476 if ((left = parseAndExp()) == NULL) 00477 return NULL; 00478 if ((tok = token) == NULL) 00479 return left; 00480 type = token->type; 00481 if (type == kxtOr || type == kxtXor) 00482 { 00483 advanceToken(); 00484 right = nextExp(); 00485 if (right == NULL) 00486 errAbort("Expecting expression on the other side of %s", tok->string); 00487 AllocVar(exp); 00488 exp->left = left; 00489 exp->right = right; 00490 if (type == kxtOr) 00491 exp->type = kxOr; 00492 else 00493 exp->type = kxXor; 00494 return exp; 00495 } 00496 else 00497 return left; 00498 }
Here is the call graph for this function:

Here is the caller graph for this function:

| static struct exp* parseParenthesized | ( | ) | [static, read] |
Definition at line 397 of file keys.c.
References advanceToken(), errAbort(), kxtCloseParen, kxtOpenParen, nextExp(), parseRelation(), token, and kxTok::type.
Referenced by parseNot().
00399 { 00400 struct exp *exp; 00401 if (token == NULL) 00402 return NULL; 00403 if (token->type == kxtOpenParen) 00404 { 00405 advanceToken(); 00406 exp = nextExp(); 00407 if (token->type != kxtCloseParen) 00408 errAbort("Unmatched parenthesis"); 00409 advanceToken(); 00410 return exp; 00411 } 00412 else 00413 { 00414 return parseRelation(); 00415 } 00416 }
Here is the call graph for this function:

Here is the caller graph for this function:

| static struct exp* parseRelation | ( | ) | [static, read] |
Definition at line 339 of file keys.c.
References advanceToken(), AllocVar, errAbort(), kxGE, kxGT, kxLE, kxLT, kxMatch, kxtEquals, kxtGE, kxtGT, kxtLE, kxtLT, kxtString, kxtWildString, kxWildMatch, exp::left, exp::right, kxTok::string, token, exp::type, and kxTok::type.
Referenced by parseParenthesized().
00341 { 00342 struct kxTok *key, *match; 00343 00344 if (token == NULL) 00345 return NULL; 00346 if (token->type != kxtString) 00347 errAbort("Expecting key got %s", token->string); 00348 key = token; 00349 advanceToken(); 00350 if (token->type == kxtEquals) 00351 { 00352 advanceToken(); 00353 if (token->type == kxtString || token->type == kxtWildString) 00354 { 00355 struct exp *exp; 00356 match = token; 00357 advanceToken(); 00358 AllocVar(exp); 00359 exp->left = key->string; 00360 exp->right = match->string; 00361 exp->type = (match->type == kxtString ? kxMatch : kxWildMatch); 00362 return exp; 00363 } 00364 else 00365 { 00366 errAbort("Expecting string to match in key=match expression,\ngot %s", token->string); 00367 } 00368 } 00369 else if (token->type == kxtGT || token->type == kxtGE || token->type == kxtLT || token->type == kxtLE) 00370 { 00371 enum kxTokType relation = token->type; 00372 advanceToken(); 00373 if (isdigit(token->string[0])) 00374 { 00375 struct exp *exp; 00376 match = token; 00377 advanceToken(); 00378 AllocVar(exp); 00379 exp->left = key->string; 00380 exp->right = match->string; 00381 if (relation == kxtGT) exp->type = kxGT; 00382 else if (relation == kxtGE) exp->type = kxGE; 00383 else if (relation == kxtLT) exp->type = kxLT; 00384 else if (relation == kxtLE) exp->type = kxLE; 00385 return exp; 00386 } 00387 else 00388 { 00389 errAbort("Expecting number got %s", token->string); 00390 } 00391 } 00392 else 00393 errAbort("Expecting = got %s", token->string); 00394 return NULL; 00395 }
Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 245 of file keys.c.
References errAbort(), getIntVals(), kvtLookup(), kxAnd, kxGE, kxGT, kxLE, kxLT, kxMatch, kxNot, kxOr, kxWildMatch, kxXor, exp::left, exp::right, sameString, sameWord, TRUE, exp::type, and wildMatch().
Referenced by keyExpEval().
00247 { 00248 if (exp == NULL) 00249 return TRUE; 00250 switch (exp->type) 00251 { 00252 case kxMatch: 00253 { 00254 char *key = exp->left; 00255 char *matcher = exp->right; 00256 char *val = kvtLookup(kvt, key); 00257 if (val == NULL) 00258 return sameWord(matcher, "null"); 00259 else 00260 return sameWord(matcher, val); 00261 } 00262 case kxWildMatch: 00263 { 00264 char *key = exp->left; 00265 char *matcher = exp->right; 00266 char *val = kvtLookup(kvt, key); 00267 if (val == NULL) 00268 return sameString(matcher, "*"); 00269 else 00270 return wildMatch(matcher, val); 00271 } 00272 case kxGT: 00273 { 00274 int left, right; 00275 getIntVals(kvt, exp, &left, &right); 00276 return left > right; 00277 } 00278 case kxGE: 00279 { 00280 int left, right; 00281 getIntVals(kvt, exp, &left, &right); 00282 return left >= right; 00283 } 00284 case kxLT: 00285 { 00286 int left, right; 00287 getIntVals(kvt, exp, &left, &right); 00288 return left < right; 00289 } 00290 case kxLE: 00291 { 00292 int left, right; 00293 getIntVals(kvt, exp, &left, &right); 00294 return left <= right; 00295 } 00296 00297 case kxNot: 00298 { 00299 return !rkeyEval(kvt, exp->right); 00300 } 00301 case kxAnd: 00302 { 00303 return rkeyEval(kvt, exp->left) && rkeyEval(kvt, exp->right); 00304 } 00305 case kxOr: 00306 { 00307 return rkeyEval(kvt, exp->left) || rkeyEval(kvt, exp->right); 00308 } 00309 case kxXor: 00310 { 00311 return rkeyEval(kvt, exp->left) ^ rkeyEval(kvt, exp->right); 00312 } 00313 default: 00314 { 00315 errAbort("unknown expression type %d", exp->type); 00316 return 0; 00317 } 00318 } 00319 }
Here is the call graph for this function:

Here is the caller graph for this function:

char const rcsid[] = "$Id: keys.c,v 1.10 2005/04/10 14:41:23 markd Exp $" [static] |
Definition at line 329 of file keys.c.
Referenced by advanceToken(), parseAndExp(), parseExp(), parseNot(), parseOrExp(), parseParenthesized(), and parseRelation().
1.5.2