예제 #1
0
TokenT *_decimal(TokenizerT *tk) {
    nextChar(tk);
    if(isdigit(tk->inputIter[0])) {
        return _decimal(tk);
    } else if(tk->inputIter[0] == '.') {
        return _float(tk, 1);
    } else if(tk->inputIter[0] == 'e' || tk->inputIter[0] == 'E') {
        return _expofloat(tk, 1, 0);
    } else {
        return makeToken(tk, "decimal integer");
    }
}
예제 #2
0
파일: vsprintf.c 프로젝트: LuoZhongYao/none
static inline char *_toNumber(char *str,long long value,_bool sign,
        HexBase base,int size,int style,int mask){
    char signString = '+';
    const char *dig = _lowerDigits;
    int tmp[64];       //缓存转换后的值.还不是ASCII 
    int length = 0;

    if(style & STYLE_LARGE) dig = _upperDigits;
    if(style & STYLE_LEFT) style &= (~STYLE_ZEROPAD); //左对齐就不能使用0填充
    //如果不是10进制,则都按无符号处理 ,并且无正负符号显示
    //如果是10进制,则去除前缀属性
    if(DECIMAL != base){
        sign = _false;
        style &= ~STYLE_SIGN;
    } else {
        style &= ~STYLE_SPECIAL;
    }

    if(style & STYLE_SPECIAL){
        if(HEX == base) size -= 2;
        else if(OCTAL == base) size -= 1;
    }

    //如果是有符号数,却小于0,则取其补码,并设置符号标志,非16进制在前面已经去除
    //符号,所以不会受影响
    if((_true == sign) && ((long long)value) < 0){
            style |= STYLE_SIGN;
            value = ~value + 1;
            signString = '-';
    }

    value &= mask;
    if(style & STYLE_SIGN) size --;

    switch(base){
        case OCTAL:length = _octal(tmp,value);break;
        case DECIMAL:length = _decimal(tmp,value);break;
        case HEX:length = _hex(tmp,value);break;
    } 
    size -= length;

    if(!(style & (STYLE_ZEROPAD|STYLE_LEFT))) while(size-- > 0) *str++ = ' ';
    if(style & STYLE_SIGN) *str++ = signString;
    if(style & STYLE_SPECIAL){
        *str++ = '0';
        if(HEX == base) *str++ = dig[0x10];
    }
    if(style & STYLE_ZEROPAD) while(size-- > 0) *str++ = '0';
    while(length-- > 0) *str++ = dig[tmp[length]];
    if(style & STYLE_LEFT) while(size-- > 0) *str++ = ' ';

    return str;
}
예제 #3
0
/*
 * TKGetNextToken returns the next token from the token stream as a
 * character string.  Space for the returned token should be dynamically
 * allocated.  The caller is responsible for freeing the space once it is
 * no longer needed.
 *
 * If the function succeeds, it returns a C string (delimited by '\0')
 * containing the token.  Else it returns 0.
 *
 * You need to fill in this function as part of your implementation.
 */
TokenT *TKGetNextToken(TokenizerT *tk) {
    clearBuffer(tk);
    char curr = tk->inputIter[0];

    // skip all whitespace before next token
    while(isspace(curr)) {
        nextChar(tk);
        clearBuffer(tk);
        curr = tk->inputIter[0];
    }

    if(curr == '\0') {
        return NULL;
    } else if(isalpha(curr) || curr == '_') {
        return _word(tk);
    } else if(curr == '0') {
        return _zero(tk);
    } else if(isdigit(curr)) {
        return _decimal(tk);
    } else if(curr == '!') { // neq
        return _neq(tk);
    } else if(curr == '"') { // double_quote
        return _double_quote(tk);
    } else if(curr == '#') {
        return _pound(tk);
    } else if(curr == '$') { // INVALID
        return _invalid(tk);
    } else if(curr == '%') { // mod, mod_eq
        return _mod(tk);
    } else if(curr == '&') { // bit_and, log_and, address (?)
        return _bit_and(tk);
    } else if(curr == '\'') { // single_quote
        return _single_quote(tk);
    } else if(curr == '(') { // open_paren
        return _open_paren(tk);
    } else if(curr == ')') { // close_paren
        return _close_paren(tk);
    } else if(curr == '*') { // mult, mult_eq, pointer (?)
        return _mult(tk);
    } else if(curr == '+') { // plus, plus_eq, inc
        return _plus(tk);
    } else if(curr == ',') { // comma
        return _comma(tk);
    } else if(curr == '-') { // minus, minus_eq, dec, struct_pointer
        return _minus(tk);
    } else if(curr == '.') { // dot
        return _dot(tk);
    } else if(curr == '/') { // div, div_eq
        return _div(tk);
    } else if(curr == ':') { // ternary_colon
        return _ternary_colon(tk);
    } else if(curr == ';') { // semicolon
        return _semicolon(tk);
    } else if(curr == '<') { // lt, lshift, lt_eq
        return _lt(tk);
    } else if(curr == '=') { // eq, assign
        return _eq(tk);
    } else if(curr == '>') { // gt, rshift, gt_eq
        return _gt(tk);
    } else if(curr == '?') { // ternary_qmark
        return _ternary_qmark(tk);
    } else if(curr == '@') { // INVALID
        return _invalid(tk);
    } else if(curr == '[') { // open_bracket
        return _open_bracket(tk);
    } else if(curr == '\\') { // backslash (?)
        return _invalid(tk);
    } else if(curr == ']') { // close_bracket
        return _close_bracket(tk);
    } else if(curr == '^') { // bit_xor
        return _bit_xor(tk);
    } else if(curr == '`') { // INVALID
        return _invalid(tk);
    } else if(curr == '{') { // open_brace
        return _open_brace(tk);
    } else if(curr == '|') { // bit_or, log_or
        return _bit_or(tk);
    } else if(curr == '}') { // close_brace
        return _close_brace(tk);
    } else if(curr == '~') { // bit_not
        return _bit_not(tk);
    } else {
        return _invalid(tk);
    }
}
예제 #4
0
int nmea_parse(char c) {
  // avoid runaway sentences (>99 chars or >29 terms) and terms (>14 chars)
  if ((n >= 100) || (_terms >= 30) || (_nt >= 15)) { _state = 0; }
  // LF and CR always reset parser
  if ((c == 0x0A) || (c == 0x0D)) { _state = 0; }
  // '$' always starts a new sentence
  if (c == '$') {
    _gprmc_tag = 0;
    _parity = 0;
    _terms = 0;
    _nt = 0;
    _sentence[0] = c;
    n = 1;
    _state = 1;
    return 0;
  }
  // parse other chars according to parser state
  switch(_state) {
  case 0:
    // waiting for '$', do nothing
    break;
  case 1:
  	// decode chars after '$' and before '*' found
    if (n < 7) {
    	// see if first seven chars match "$GPRMC,"
    	if (c == _GPRMC_TERM[n]) { _gprmc_tag++; }
    }
    // add received char to sentence
    _sentence[n++] = c;
    switch (c) {
    case ',':
    	// ',' delimits the individual terms
      (_term[_terms++])[_nt] = 0;
      _nt = 0;
      _parity = _parity ^ c;
      break;
    case '*':
    	// '*' delimits term and precedes checksum term
      (_term[_terms++])[_nt] = 0;
      _nt = 0;
      _state++;
      break;
    default:
    	// all other chars between '$' and '*' are part of a term
      (_term[_terms])[_nt++] = c;
      _parity = _parity ^ c;
      break;
    }
    break;
  case 2:
  	// first char following '*' is checksum MSB
    _sentence[n++] = c;
    (_term[_terms])[_nt++] = c;
    _parity = _parity - (16 * _dehex(c));		// replace with bitshift?
    _state++;
    break;
  case 3:
  	// second char after '*' completes the checksum (LSB)
    _sentence[n++] = c;
    _sentence[n++] = 0;
    (_term[_terms])[_nt++] = c;
    (_term[_terms++])[_nt] = 0;
    _state = 0;
    _parity = _parity - _dehex(c);
    // when parity is zero, checksum was correct!
    if (_parity == 0) {
    	// accept all sentences, or only GPRMC datatype?
    	if ((!_gprmc_only) || (_gprmc_tag == 6)) {
	    	// copy _sentence[] to f_sentence[]
	    	while ((--n) >= 0) { f_sentence[n] = _sentence[n]; }
	    	// copy all _terms[] to f_terms[]
	      for (f_terms=0; f_terms<_terms; f_terms++) {
	      	_nt = 0;
	      	while ((_term[f_terms])[_nt]) {
	        	(f_term[f_terms])[_nt] = (_term[f_terms])[_nt];
	        	_nt++;
	        }
	        (f_term[f_terms])[_nt] = 0;
	      }
	      // when sentence is of datatype GPRMC
	      if (_gprmc_tag == 6) {
	      	// store values of relevant GPRMC terms
	      	_gprmc_utc = _decimal(_term[1]);
	      	_gprmc_status = (_term[2])[0];
	        // calculate signed degree-decimal value of latitude term
	        _gprmc_lat = _decimal(_term[3]) / 100.0;
	        _degs = floor(_gprmc_lat);
	        _gprmc_lat = (100.0 * (_gprmc_lat - _degs)) / 60.0;
	        _gprmc_lat += _degs;
	        // southern hemisphere is negative-valued
	        if ((_term[4])[0] == 'S') {
	          _gprmc_lat = 0.0 - _gprmc_lat;
	        }
	        // calculate signed degree-decimal value of longitude term
	        _gprmc_long = _decimal(_term[5]) / 100.0;
	        _degs = floor(_gprmc_long);
	        _gprmc_long = (100.0 * (_gprmc_long - _degs)) / 60.0;
	        _gprmc_long += _degs;
	        // western hemisphere is negative-valued
	        if ((_term[6])[0] == 'W') {
	          _gprmc_long = 0.0 - _gprmc_long;
	        }
	        _gprmc_speed = _decimal(_term[7]);
	        _gprmc_angle = _decimal(_term[8]);
	      }
      	// sentence accepted!
      	return 1;
      }
    }
    break;
  default:
    _state = 0;
    break;
  }
  return 0;
}
예제 #5
0
float nmea_term_decimal(int t) {
	// returns value of decimally coded term t
  return _decimal(f_term[t]);
}