diff --git a/qse/cmd/awk/awk.c b/qse/cmd/awk/awk.c index ea442718..ea88f397 100644 --- a/qse/cmd/awk/awk.c +++ b/qse/cmd/awk/awk.c @@ -1,5 +1,5 @@ /* - * $Id: awk.c 86 2009-02-26 12:55:05Z hyunghwan.chung $ + * $Id: awk.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -154,7 +154,7 @@ static qse_map_walk_t print_awk_value ( qse_char_t* str; qse_size_t len; - str = qse_awk_rtx_valtostr (run, QSE_MAP_VPTR(pair), 0, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (run, QSE_MAP_VPTR(pair), &len); if (str == QSE_NULL) { dprint (QSE_T("***OUT OF MEMORY***\n")); @@ -209,7 +209,7 @@ static void on_run_exit ( } else { - str = qse_awk_rtx_valtostr (rtx, ret, 0, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (rtx, ret, &len); if (str == QSE_NULL) { dprint (QSE_T("[RETURN] - ***OUT OF MEMORY***\n")); diff --git a/qse/include/qse/awk/awk.h b/qse/include/qse/awk/awk.h index ea799b62..1f51bd43 100644 --- a/qse/include/qse/awk/awk.h +++ b/qse/include/qse/awk/awk.h @@ -1,5 +1,5 @@ /* - * $Id: awk.h 88 2009-02-28 08:44:21Z hyunghwan.chung $ + * $Id: awk.h 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -1590,16 +1590,6 @@ qse_bool_t qse_awk_rtx_valtobool ( qse_awk_val_t* val ); -#if 0 -qse_char_t* qse_awk_rtx_valtostr ( - qse_awk_rtx_t* rtx, - qse_awk_val_t* val, - int opt, - qse_str_t* buf, - qse_size_t* len -); -#endif - /****f* AWK/qse_awk_rtx_valtostr * NAME * qse_awk_rtx_valtostr - convert a value to a string @@ -1612,6 +1602,18 @@ qse_char_t* qse_awk_rtx_valtostr ( ); /******/ +/****f* AWK/qse_awk_rtx_valtostrdup + * NAME + * qse_awk_rtx_valtostrdup - convert a value to a duplicated string + * SYNOPSIS + */ +qse_char_t* qse_awk_rtx_valtostrdup ( + qse_awk_rtx_t* rtx, + qse_awk_val_t* v, + qse_size_t* len +); +/******/ + /****f* AWK/qse_awk_rtx_valtonum * NAME * qse_awk_rtx_valtonum - convert a value to a number @@ -1657,6 +1659,16 @@ int qse_awk_rtx_strtonum ( ); /******/ +void* qse_awk_rtx_alloc ( + qse_awk_rtx_t* rtx, + qse_size_t size +); + +void qse_awk_rtx_free ( + qse_awk_rtx_t* rtx, + void* ptr +); + #ifdef __cplusplus } #endif diff --git a/qse/lib/awk/Awk.cpp b/qse/lib/awk/Awk.cpp index 80081f93..aa5c13f0 100644 --- a/qse/lib/awk/Awk.cpp +++ b/qse/lib/awk/Awk.cpp @@ -1,5 +1,5 @@ /* - * $Id: Awk.cpp 84 2009-02-25 10:35:22Z hyunghwan.chung $ + * $Id: Awk.cpp 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -340,8 +340,8 @@ int Awk::Argument::init (val_t* v) this->inum = ((qse_awk_val_int_t*)v)->val; this->rnum = (qse_real_t)((qse_awk_val_int_t*)v)->val; - this->str.ptr = qse_awk_rtx_valtostr ( - this->run->run, v, 0, QSE_NULL, &this->str.len); + this->str.ptr = qse_awk_rtx_valtostrdup ( + this->run->run, v, &this->str.len); if (this->str.ptr != QSE_NULL) return 0; } else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_REAL) @@ -349,8 +349,8 @@ int Awk::Argument::init (val_t* v) this->inum = (qse_long_t)((qse_awk_val_real_t*)v)->val; this->rnum = ((qse_awk_val_real_t*)v)->val; - this->str.ptr = qse_awk_rtx_valtostr ( - this->run->run, v, 0, QSE_NULL, &this->str.len); + this->str.ptr = qse_awk_rtx_valtostrdup ( + this->run->run, v, &this->str.len); if (this->str.ptr != QSE_NULL) return 0; } else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_NIL) @@ -358,8 +358,8 @@ int Awk::Argument::init (val_t* v) this->inum = 0; this->rnum = 0.0; - this->str.ptr = qse_awk_rtx_valtostr ( - this->run->run, v, 0, QSE_NULL, &this->str.len); + this->str.ptr = qse_awk_rtx_valtostrdup ( + this->run->run, v, &this->str.len); if (this->str.ptr != QSE_NULL) return 0; } else if (QSE_AWK_VAL_TYPE(v) == QSE_AWK_VAL_MAP) diff --git a/qse/lib/awk/awk.c b/qse/lib/awk/awk.c index 826c41fb..32c184cb 100644 --- a/qse/lib/awk/awk.c +++ b/qse/lib/awk/awk.c @@ -1,5 +1,5 @@ /* - * $Id: awk.c 85 2009-02-26 10:56:12Z hyunghwan.chung $ + * $Id: awk.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -49,7 +49,6 @@ static void free_fnc (qse_map_t* map, void* vptr, qse_size_t vlen) { qse_awk_t* awk = *(qse_awk_t**)QSE_XTN(map); qse_awk_fnc_t* f = (qse_awk_fnc_t*)vptr; - QSE_AWK_FREE (awk, f); } diff --git a/qse/lib/awk/fnc.c b/qse/lib/awk/fnc.c index 13b422c9..51535fa5 100644 --- a/qse/lib/awk/fnc.c +++ b/qse/lib/awk/fnc.c @@ -1,5 +1,5 @@ /* - * $Id: fnc.c 75 2009-02-22 14:10:34Z hyunghwan.chung $ + * $Id: fnc.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -249,8 +249,7 @@ static int fnc_close ( } else { - name = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); + name = qse_awk_rtx_valtostrdup (run, a0, &len); if (name == QSE_NULL) return -1; } @@ -363,10 +362,8 @@ static int fnc_fflush ( } else { - str0 = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len0); + str0 = qse_awk_rtx_valtostrdup (run, a0, &len0); if (str0 == QSE_NULL) return -1; - } /* the target name contains a null character. @@ -436,8 +433,7 @@ static int fnc_index ( } else { - str0 = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len0); + str0 = qse_awk_rtx_valtostrdup (run, a0, &len0); if (str0 == QSE_NULL) return -1; } @@ -448,8 +444,7 @@ static int fnc_index ( } else { - str1 = qse_awk_rtx_valtostr ( - run, a1, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len1); + str1 = qse_awk_rtx_valtostrdup (run, a1, &len1); if (str1 == QSE_NULL) { if (a0->type != QSE_AWK_VAL_STR) @@ -493,8 +488,7 @@ static int fnc_length ( } else { - str = qse_awk_rtx_valtostr ( - run, v, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (run, v, &len); if (str == QSE_NULL) return -1; QSE_AWK_FREE (run->awk, str); } @@ -535,8 +529,7 @@ static int fnc_substr ( } else { - str = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (run, a0, &len); if (str == QSE_NULL) return -1; } @@ -641,8 +634,7 @@ static int fnc_split ( } else { - str = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &str_len); + str = qse_awk_rtx_valtostrdup (run, a0, &str_len); if (str == QSE_NULL) return -1; str_free = str; } @@ -665,8 +657,7 @@ static int fnc_split ( } else { - fs_ptr = qse_awk_rtx_valtostr ( - run, t1, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &fs_len); + fs_ptr = qse_awk_rtx_valtostrdup (run, t1, &fs_len); if (fs_ptr == QSE_NULL) { if (str_free != QSE_NULL) @@ -692,8 +683,7 @@ static int fnc_split ( } else { - fs_ptr = qse_awk_rtx_valtostr ( - run, a2, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &fs_len); + fs_ptr = qse_awk_rtx_valtostrdup (run, a2, &fs_len); if (fs_ptr == QSE_NULL) { if (str_free != QSE_NULL) @@ -860,8 +850,7 @@ static int fnc_tolower ( } else { - str = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (run, a0, &len); if (str == QSE_NULL) return -1; } @@ -900,8 +889,7 @@ static int fnc_toupper ( } else { - str = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (run, a0, &len); if (str == QSE_NULL) return -1; } @@ -967,8 +955,7 @@ static int __substitute (qse_awk_rtx_t* run, qse_long_t max_count) } else { - a0_ptr = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &a0_len); + a0_ptr = qse_awk_rtx_valtostrdup (run, a0, &a0_len); if (a0_ptr == QSE_NULL) { FREE_A_PTRS (run->awk); @@ -984,8 +971,7 @@ static int __substitute (qse_awk_rtx_t* run, qse_long_t max_count) } else { - a1_ptr = qse_awk_rtx_valtostr ( - run, a1, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &a1_len); + a1_ptr = qse_awk_rtx_valtostrdup (run, a1, &a1_len); if (a1_ptr == QSE_NULL) { FREE_A_PTRS (run->awk); @@ -1040,8 +1026,7 @@ static int __substitute (qse_awk_rtx_t* run, qse_long_t max_count) } else { - a2_ptr = qse_awk_rtx_valtostr ( - run, *a2_ref, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &a2_len); + a2_ptr = qse_awk_rtx_valtostrdup (run, *a2_ref, &a2_len); if (a2_ptr == QSE_NULL) { FREE_A_PTRS (run->awk); @@ -1249,8 +1234,7 @@ static int fnc_match ( } else { - str0 = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len0); + str0 = qse_awk_rtx_valtostrdup (run, a0, &len0); if (str0 == QSE_NULL) return -1; } @@ -1267,8 +1251,7 @@ static int fnc_match ( } else { - str1 = qse_awk_rtx_valtostr ( - run, a1, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len1); + str1 = qse_awk_rtx_valtostrdup (run, a1, &len1); if (str1 == QSE_NULL) { if (a0->type != QSE_AWK_VAL_STR) @@ -1373,8 +1356,7 @@ static int fnc_sprintf ( } else { - cs0.ptr = qse_awk_rtx_valtostr ( - run, a0, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &cs0.len); + cs0.ptr = qse_awk_rtx_valtostrdup (run, a0, &cs0.len); if (cs0.ptr == QSE_NULL) { qse_str_fini (&fbu); diff --git a/qse/lib/awk/misc.c b/qse/lib/awk/misc.c index 489aeeb5..427735c7 100644 --- a/qse/lib/awk/misc.c +++ b/qse/lib/awk/misc.c @@ -1,5 +1,5 @@ /* - * $Id: misc.c 75 2009-02-22 14:10:34Z hyunghwan.chung $ + * $Id: misc.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -966,3 +966,14 @@ int qse_awk_matchrex ( if (x < 0) *errnum = QSE_AWK_REXERRTOERR(err); return x; } + +void* qse_awk_rtx_alloc (qse_awk_rtx_t* rtx, qse_size_t size) +{ + return qse_awk_alloc (rtx->awk, size); +} + +void qse_awk_rtx_free (qse_awk_rtx_t* rtx, void* ptr) +{ + qse_awk_free (rtx->awk, ptr); +} + diff --git a/qse/lib/awk/rec.c b/qse/lib/awk/rec.c index 0ce63375..68ef57e5 100644 --- a/qse/lib/awk/rec.c +++ b/qse/lib/awk/rec.c @@ -1,5 +1,5 @@ /* - * $Id: rec.c 75 2009-02-22 14:10:34Z hyunghwan.chung $ + * $Id: rec.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -122,9 +122,13 @@ static int split_record (qse_awk_rtx_t* run) } else { - fs_ptr = qse_awk_rtx_valtostr ( - run, fs, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &fs_len); - if (fs_ptr == QSE_NULL) return -1; + qse_awk_rtx_valtostr_out_t out; + + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, fs, &out) == QSE_NULL) return -1; + + fs_ptr = out.u.cpldup.ptr; + fs_len = out.u.cpldup.len; fs_free = fs_ptr; } diff --git a/qse/lib/awk/rio.c b/qse/lib/awk/rio.c index 46004746..e9a78753 100644 --- a/qse/lib/awk/rio.c +++ b/qse/lib/awk/rio.c @@ -1,5 +1,5 @@ /* - * $Id: rio.c 75 2009-02-22 14:10:34Z hyunghwan.chung $ + * $Id: rio.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -217,8 +217,7 @@ int qse_awk_rtx_readio ( } else { - rs_ptr = qse_awk_rtx_valtostr ( - run, rs, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &rs_len); + rs_ptr = qse_awk_rtx_valtostrdup (run, rs, &rs_len); if (rs_ptr == QSE_NULL) { qse_awk_rtx_refdownval (run, rs); @@ -424,11 +423,14 @@ int qse_awk_rtx_writeio_val ( } else { - str = qse_awk_rtx_valtostr ( - run, v, - QSE_AWK_RTX_VALTOSTR_CLEAR | QSE_AWK_RTX_VALTOSTR_PRINT, - QSE_NULL, &len); - if (str == QSE_NULL) return -1; + qse_awk_rtx_valtostr_out_t out; + + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP | + QSE_AWK_RTX_VALTOSTR_PRINT; + if (qse_awk_rtx_valtostr (run, v, &out) == QSE_NULL) return -1; + + str = out.u.cpldup.ptr; + len = out.u.cpldup.len; } n = qse_awk_rtx_writeio_str (run, out_type, name, str, len); diff --git a/qse/lib/awk/run.c b/qse/lib/awk/run.c index da6dcb03..921b73a2 100644 --- a/qse/lib/awk/run.c +++ b/qse/lib/awk/run.c @@ -1,5 +1,5 @@ /* - * $Id: run.c 88 2009-02-28 08:44:21Z hyunghwan.chung $ + * $Id: run.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -2694,6 +2694,7 @@ static int run_delete (qse_awk_rtx_t* run, qse_awk_nde_delete_t* nde) qse_size_t keylen; qse_awk_val_t* idx; qse_char_t buf[IDXBUFSIZE]; + qse_awk_rtx_valtostr_out_t out; QSE_ASSERT (var->idx != QSE_NULL); @@ -2703,16 +2704,24 @@ static int run_delete (qse_awk_rtx_t* run, qse_awk_nde_delete_t* nde) qse_awk_rtx_refupval (run, idx); /* try with a fixed-size buffer */ - keylen = QSE_COUNTOF(buf); - key = qse_awk_rtx_valtostr ( - run, idx, QSE_AWK_RTX_VALTOSTR_FIXED, - (qse_str_t*)buf, &keylen); - if (key == QSE_NULL) + out.type = QSE_AWK_RTX_VALTOSTR_CPL; + out.u.cpl.ptr = buf; + out.u.cpl.len = QSE_COUNTOF(buf); + if (qse_awk_rtx_valtostr (run, idx, &out) == QSE_NULL) { /* if it doesn't work, switch to dynamic mode */ - key = qse_awk_rtx_valtostr ( - run, idx, QSE_AWK_RTX_VALTOSTR_CLEAR, - QSE_NULL, &keylen); + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, idx, &out) != QSE_NULL) + { + key = out.u.cpldup.ptr; + keylen = out.u.cpldup.len; + } + } + else + { + key = out.u.cpl.ptr; + keylen = out.u.cpl.len; + QSE_ASSERT (key == buf); } qse_awk_rtx_refdownval (run, idx); @@ -2722,6 +2731,7 @@ static int run_delete (qse_awk_rtx_t* run, qse_awk_nde_delete_t* nde) run->errlin = var->line; return -1; } + qse_map_delete (map, key, keylen); if (key != buf) QSE_AWK_FREE (run->awk, key); } @@ -2817,6 +2827,7 @@ static int run_print (qse_awk_rtx_t* run, qse_awk_nde_print_t* nde) /* check if destination has been specified. */ if (nde->out != QSE_NULL) { + qse_awk_rtx_valtostr_out_t vsout; qse_size_t len; /* if so, resolve the destination name */ @@ -2824,16 +2835,18 @@ static int run_print (qse_awk_rtx_t* run, qse_awk_nde_print_t* nde) if (v == QSE_NULL) return -1; qse_awk_rtx_refupval (run, v); - out = qse_awk_rtx_valtostr ( - run, v, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (out == QSE_NULL) + + vsout.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, v, &vsout) == QSE_NULL) { qse_awk_rtx_refdownval (run, v); - /* change the error line */ run->errlin = nde->line; return -1; } + out = vsout.u.cpldup.ptr; + len = vsout.u.cpldup.len; + qse_awk_rtx_refdownval (run, v); if (len <= 0) @@ -2977,21 +2990,23 @@ static int run_printf (qse_awk_rtx_t* run, qse_awk_nde_print_t* nde) if (nde->out != QSE_NULL) { qse_size_t len; + qse_awk_rtx_valtostr_out_t vsout; v = eval_expression (run, nde->out); if (v == QSE_NULL) return -1; qse_awk_rtx_refupval (run, v); - out = qse_awk_rtx_valtostr ( - run, v, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (out == QSE_NULL) + + vsout.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, v, &vsout) == QSE_NULL) { qse_awk_rtx_refdownval (run, v); - - /* change the error line */ - run->errlin = nde->line; + run->errlin = nde->line; /* change the error line */ return -1; } + out = vsout.u.cpldup.ptr; + len = vsout.u.cpldup.len; + qse_awk_rtx_refdownval (run, v); if (len <= 0) @@ -3569,11 +3584,15 @@ static qse_awk_val_t* do_assignment_map ( len = QSE_COUNTOF(idxbuf); str = idxnde_to_str (run, var->idx, idxbuf, &len); +/* TODO: VERIFY if (str == QSE_NULL) { str = idxnde_to_str (run, var->idx, QSE_NULL, &len); +*/ if (str == QSE_NULL) return QSE_NULL; +/* } +*/ #ifdef DEBUG_RUN qse_dprintf (QSE_T("**** index str=>%s, map->ref=%d, map->type=%d\n"), @@ -3630,14 +3649,18 @@ static qse_awk_val_t* do_assignment_pos ( } else { - str = qse_awk_rtx_valtostr ( - run, val, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (str == QSE_NULL) + qse_awk_rtx_valtostr_out_t out; + + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, val, &out) == QSE_NULL) { /* change error line */ run->errlin = pos->line; return QSE_NULL; } + + str = out.u.cpldup.ptr; + len = out.u.cpldup.len; } n = qse_awk_rtx_setrec (run, (qse_size_t)lv, str, len); @@ -3873,13 +3896,17 @@ static qse_awk_val_t* eval_binop_in ( str = (left->type == QSE_AWK_NDE_GRP)? idxnde_to_str (run, ((qse_awk_nde_grp_t*)left)->body, idxbuf, &len): idxnde_to_str (run, left, idxbuf, &len); +/* TODO: VERIFY if (str == QSE_NULL) { str = (left->type == QSE_AWK_NDE_GRP)? idxnde_to_str (run, ((qse_awk_nde_grp_t*)left)->body, QSE_NULL, &len): idxnde_to_str (run, left, QSE_NULL, &len); +*/ if (str == QSE_NULL) return QSE_NULL; +/* } +*/ /* evaluate the right-hand side of the operator */ QSE_ASSERT (right->next == QSE_NULL); @@ -4051,30 +4078,36 @@ static int __cmp_int_real ( static int __cmp_int_str ( qse_awk_rtx_t* run, qse_awk_val_t* left, qse_awk_val_t* right) { - qse_char_t* str; - qse_size_t len; + const qse_char_t* end; + qse_awk_rtx_valtostr_out_t out; qse_long_t r; - qse_real_t rr; int n; - r = qse_awk_strxtolong (run->awk, + r = qse_awk_strxtolong ( + run->awk, ((qse_awk_val_str_t*)right)->ptr, - ((qse_awk_val_str_t*)right)->len, 0, (const qse_char_t**)&str); - if (str == ((qse_awk_val_str_t*)right)->ptr + + ((qse_awk_val_str_t*)right)->len, 0, + &end + ); + if (end == ((qse_awk_val_str_t*)right)->ptr + ((qse_awk_val_str_t*)right)->len) { if (((qse_awk_val_int_t*)left)->val > r) return 1; if (((qse_awk_val_int_t*)left)->val < r) return -1; return 0; } -/* TODO: should i do this??? conversion to real and comparision... */ - else if (*str == QSE_T('.') || *str == QSE_T('E') || *str == QSE_T('e')) + /* TODO: should i conver it to real and compare? */ + else if (*end == QSE_T('.') || *end == QSE_T('E') || *end == QSE_T('e')) { - rr = qse_awk_strxtoreal (run->awk, + qse_real_t rr; + + rr = qse_awk_strxtoreal ( + run->awk, ((qse_awk_val_str_t*)right)->ptr, ((qse_awk_val_str_t*)right)->len, - (const qse_char_t**)&str); - if (str == ((qse_awk_val_str_t*)right)->ptr + + &end + ); + if (end == ((qse_awk_val_str_t*)right)->ptr + ((qse_awk_val_str_t*)right)->len) { if (((qse_awk_val_int_t*)left)->val > rr) return 1; @@ -4083,27 +4116,31 @@ static int __cmp_int_str ( } } - str = qse_awk_rtx_valtostr ( - run, left, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (str == QSE_NULL) return CMP_ERROR; + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, left, &out) == QSE_NULL) + return CMP_ERROR; if (run->gbl.ignorecase) { n = qse_strxncasecmp ( - str, len, + out.u.cpldup.ptr, + out.u.cpldup.len, ((qse_awk_val_str_t*)right)->ptr, ((qse_awk_val_str_t*)right)->len, - &run->awk->ccls); + &run->awk->ccls + ); } else { n = qse_strxncmp ( - str, len, + out.u.cpldup.ptr, + out.u.cpldup.len, ((qse_awk_val_str_t*)right)->ptr, - ((qse_awk_val_str_t*)right)->len); + ((qse_awk_val_str_t*)right)->len + ); } - QSE_AWK_FREE (run->awk, str); + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); return n; } @@ -4138,16 +4175,18 @@ static int __cmp_real_real ( static int __cmp_real_str ( qse_awk_rtx_t* run, qse_awk_val_t* left, qse_awk_val_t* right) { - qse_char_t* str; - qse_size_t len; + qse_awk_rtx_valtostr_out_t out; + const qse_char_t* end; qse_real_t rr; int n; - rr = qse_awk_strxtoreal (run->awk, + rr = qse_awk_strxtoreal ( + run->awk, ((qse_awk_val_str_t*)right)->ptr, ((qse_awk_val_str_t*)right)->len, - (const qse_char_t**)&str); - if (str == ((qse_awk_val_str_t*)right)->ptr + + &end + ); + if (end == ((qse_awk_val_str_t*)right)->ptr + ((qse_awk_val_str_t*)right)->len) { if (((qse_awk_val_real_t*)left)->val > rr) return 1; @@ -4155,27 +4194,31 @@ static int __cmp_real_str ( return 0; } - str = qse_awk_rtx_valtostr ( - run, left, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (str == QSE_NULL) return CMP_ERROR; + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, left, &out) == QSE_NULL) + return CMP_ERROR; if (run->gbl.ignorecase) { n = qse_strxncasecmp ( - str, len, + out.u.cpldup.ptr, + out.u.cpldup.len, ((qse_awk_val_str_t*)right)->ptr, ((qse_awk_val_str_t*)right)->len, - &run->awk->ccls); + &run->awk->ccls + ); } else { n = qse_strxncmp ( - str, len, + out.u.cpldup.ptr, + out.u.cpldup.len, ((qse_awk_val_str_t*)right)->ptr, - ((qse_awk_val_str_t*)right)->len); + ((qse_awk_val_str_t*)right)->len + ); } - QSE_AWK_FREE (run->awk, str); + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); return n; } @@ -4671,26 +4714,30 @@ static qse_awk_val_t* eval_binop_exp ( static qse_awk_val_t* eval_binop_concat ( qse_awk_rtx_t* run, qse_awk_val_t* left, qse_awk_val_t* right) { - qse_char_t* strl, * strr; - qse_size_t strl_len, strr_len; qse_awk_val_t* res; + qse_awk_rtx_valtostr_out_t lout, rout; - strl = qse_awk_rtx_valtostr ( - run, left, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &strl_len); - if (strl == QSE_NULL) return QSE_NULL; - - strr = qse_awk_rtx_valtostr ( - run, right, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &strr_len); - if (strr == QSE_NULL) + lout.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, left, &lout) == QSE_NULL) { - QSE_AWK_FREE (run->awk, strl); return QSE_NULL; } - res = qse_awk_rtx_makestrval2 (run, strl, strl_len, strr, strr_len); + rout.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, right, &rout) == QSE_NULL) + { + QSE_AWK_FREE (run->awk, lout.u.cpldup.ptr); + return QSE_NULL; + } - QSE_AWK_FREE (run->awk, strl); - QSE_AWK_FREE (run->awk, strr); + res = qse_awk_rtx_makestrval2 ( + run, + lout.u.cpldup.ptr, lout.u.cpldup.len, + rout.u.cpldup.ptr, rout.u.cpldup.len + ); + + QSE_AWK_FREE (run->awk, rout.u.cpldup.ptr); + QSE_AWK_FREE (run->awk, lout.u.cpldup.ptr); return res; } @@ -4762,8 +4809,6 @@ static qse_awk_val_t* eval_binop_match0 ( { qse_awk_val_t* res; int n, errnum; - qse_char_t* str; - qse_size_t len; void* rex_code; if (right->type == QSE_AWK_VAL_REX) @@ -4784,20 +4829,22 @@ static qse_awk_val_t* eval_binop_match0 ( } else { - str = qse_awk_rtx_valtostr ( - run, right, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (str == QSE_NULL) return QSE_NULL; + qse_awk_rtx_valtostr_out_t out; - rex_code = QSE_AWK_BUILDREX (run->awk, str, len, &errnum); + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, right, &out) == QSE_NULL) + return QSE_NULL; + + rex_code = QSE_AWK_BUILDREX ( + run->awk, out.u.cpldup.ptr, out.u.cpldup.len, &errnum); if (rex_code == QSE_NULL) { - QSE_AWK_FREE (run->awk, str); - + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); qse_awk_rtx_seterror (run, errnum, rline, QSE_NULL); return QSE_NULL; } - QSE_AWK_FREE (run->awk, str); + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); } if (left->type == QSE_AWK_VAL_STR) @@ -4830,9 +4877,10 @@ static qse_awk_val_t* eval_binop_match0 ( } else { - str = qse_awk_rtx_valtostr ( - run, left, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (str == QSE_NULL) + qse_awk_rtx_valtostr_out_t out; + + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, left, &out) == QSE_NULL) { if (right->type != QSE_AWK_VAL_REX) QSE_AWK_FREE (run->awk, rex_code); @@ -4842,10 +4890,11 @@ static qse_awk_val_t* eval_binop_match0 ( n = QSE_AWK_MATCHREX ( run->awk, rex_code, ((run->gbl.ignorecase)? QSE_REX_IGNORECASE: 0), - str, len, QSE_NULL, QSE_NULL, &errnum); + out.u.cpldup.ptr, out.u.cpldup.len, + QSE_NULL, QSE_NULL, &errnum); if (n == -1) { - QSE_AWK_FREE (run->awk, str); + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); if (right->type != QSE_AWK_VAL_REX) QSE_AWK_FREE (run->awk, rex_code); @@ -4856,7 +4905,7 @@ static qse_awk_val_t* eval_binop_match0 ( res = qse_awk_rtx_makeintval (run, (n == ret)); if (res == QSE_NULL) { - QSE_AWK_FREE (run->awk, str); + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); if (right->type != QSE_AWK_VAL_REX) QSE_AWK_FREE (run->awk, rex_code); @@ -4865,7 +4914,7 @@ static qse_awk_val_t* eval_binop_match0 ( return QSE_NULL; } - QSE_AWK_FREE (run->awk, str); + QSE_AWK_FREE (run->awk, out.u.cpldup.ptr); } if (right->type != QSE_AWK_VAL_REX) QSE_AWK_FREE (run->awk, rex_code); @@ -6032,11 +6081,15 @@ static qse_awk_val_t** get_reference_indexed ( len = QSE_COUNTOF(idxbuf); str = idxnde_to_str (run, nde->idx, idxbuf, &len); +/* TODO: VERIFY if (str == QSE_NULL) { str = idxnde_to_str (run, nde->idx, QSE_NULL, &len); +*/ if (str == QSE_NULL) return QSE_NULL; +/* } +*/ pair = qse_map_search ((*(qse_awk_val_map_t**)val)->map, str, len); if (pair == QSE_NULL) @@ -6184,11 +6237,15 @@ static qse_awk_val_t* eval_indexed ( len = QSE_COUNTOF(idxbuf); str = idxnde_to_str (run, nde->idx, idxbuf, &len); +/* TODO: VERIFY if (str == QSE_NULL) { str = idxnde_to_str (run, nde->idx, QSE_NULL, &len); +*/ if (str == QSE_NULL) return QSE_NULL; +/* } +*/ pair = qse_map_search ((*(qse_awk_val_map_t**)val)->map, str, len); if (str != idxbuf) QSE_AWK_FREE (run->awk, str); @@ -6294,6 +6351,7 @@ static qse_awk_val_t* eval_getline (qse_awk_rtx_t* run, qse_awk_nde_t* nde) if (p->in != QSE_NULL) { qse_size_t len; + qse_awk_rtx_valtostr_out_t out; v = eval_expression (run, p->in); if (v == QSE_NULL) return QSE_NULL; @@ -6304,15 +6362,18 @@ static qse_awk_val_t* eval_getline (qse_awk_rtx_t* run, qse_awk_nde_t* nde) * v->type == QSE_AWK_VAL_STR, qse_awk_rtx_refdownval(v) * should not be called immediately below */ qse_awk_rtx_refupval (run, v); - in = qse_awk_rtx_valtostr ( - run, v, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); - if (in == QSE_NULL) + + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, v, &out) == QSE_NULL) { qse_awk_rtx_refdownval (run, v); return QSE_NULL; } qse_awk_rtx_refdownval (run, v); + in = out.u.cpldup.ptr; + len = out.u.cpldup.len; + if (len <= 0) { /* the input source name is empty. @@ -6499,11 +6560,16 @@ static int shorten_record (qse_awk_rtx_t* run, qse_size_t nflds) } else { - ofs = qse_awk_rtx_valtostr ( - run, v, QSE_AWK_RTX_VALTOSTR_CLEAR, - QSE_NULL, &ofs_len); - if (ofs == QSE_NULL) return -1; + qse_awk_rtx_valtostr_out_t out; + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, v, &out) == QSE_NULL) + { + return -1; + } + + ofs = out.u.cpldup.ptr; + ofs_len = out.u.cpldup.len; ofs_free = ofs; } } @@ -6511,6 +6577,9 @@ static int shorten_record (qse_awk_rtx_t* run, qse_size_t nflds) if (qse_str_init ( &tmp, MMGR(run), QSE_STR_LEN(&run->inrec.line)) == QSE_NULL) { + if (ofs_free != QSE_NULL) + QSE_AWK_FREE (run->awk, ofs_free); + if (nflds > 1) qse_awk_rtx_refdownval (run, v); qse_awk_rtx_seterrnum (run, QSE_AWK_ENOMEM); return -1; } @@ -6519,6 +6588,7 @@ static int shorten_record (qse_awk_rtx_t* run, qse_size_t nflds) { if (i > 0 && qse_str_ncat(&tmp,ofs,ofs_len) == (qse_size_t)-1) { + qse_str_fini (&tmp); if (ofs_free != QSE_NULL) QSE_AWK_FREE (run->awk, ofs_free); if (nflds > 1) qse_awk_rtx_refdownval (run, v); @@ -6530,10 +6600,10 @@ static int shorten_record (qse_awk_rtx_t* run, qse_size_t nflds) run->inrec.flds[i].ptr, run->inrec.flds[i].len) == (qse_size_t)-1) { + qse_str_fini (&tmp); if (ofs_free != QSE_NULL) QSE_AWK_FREE (run->awk, ofs_free); if (nflds > 1) qse_awk_rtx_refdownval (run, v); - qse_awk_rtx_seterrnum (run, QSE_AWK_ENOMEM); return -1; } @@ -6544,7 +6614,11 @@ static int shorten_record (qse_awk_rtx_t* run, qse_size_t nflds) v = (qse_awk_val_t*) qse_awk_rtx_makestrval ( run, QSE_STR_PTR(&tmp), QSE_STR_LEN(&tmp)); - if (v == QSE_NULL) return -1; + if (v == QSE_NULL) + { + qse_str_fini (&tmp); + return -1; + } qse_awk_rtx_refdownval (run, run->inrec.d0); run->inrec.d0 = v; @@ -6572,6 +6646,8 @@ static qse_char_t* idxnde_to_str ( if (nde->next == QSE_NULL) { + qse_awk_rtx_valtostr_out_t out; + /* single node index */ idx = eval_expression (run, nde); if (idx == QSE_NULL) return QSE_NULL; @@ -6582,24 +6658,33 @@ static qse_char_t* idxnde_to_str ( if (buf != QSE_NULL) { - /* try with a fixed-size buffer */ - str = qse_awk_rtx_valtostr ( - run, idx, QSE_AWK_RTX_VALTOSTR_FIXED, (qse_str_t*)buf, len); + /* try with a fixed-size buffer if given */ + out.type = QSE_AWK_RTX_VALTOSTR_CPL; + out.u.cpl.ptr = buf; + out.u.cpl.len = *len; + + if (qse_awk_rtx_valtostr (run, idx, &out) != QSE_NULL) + { + str = out.u.cpl.ptr; + *len = out.u.cpl.len; + QSE_ASSERT (str == buf); + } } if (str == QSE_NULL) { - /* if it doen't work, switch to the dynamic mode */ - str = qse_awk_rtx_valtostr ( - run, idx, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, len); - - if (str == QSE_NULL) + /* if no fixed-size buffer was given or the fixed-size + * conversion failed, switch to the dynamic mode */ + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, idx, &out) == QSE_NULL) { qse_awk_rtx_refdownval (run, idx); - /* change error line */ - run->errlin = nde->line; + run->errlin = nde->line; /* adjust error line */ return QSE_NULL; } + + str = out.u.cpldup.ptr; + *len = out.u.cpldup.len; } qse_awk_rtx_refdownval (run, idx); @@ -6609,6 +6694,10 @@ static qse_char_t* idxnde_to_str ( /* multidimensional index */ qse_str_t idxstr; qse_xstr_t tmp; + qse_awk_rtx_valtostr_out_t out; + + out.type = QSE_AWK_RTX_VALTOSTR_STRPCAT; + out.u.strpcat = &idxstr; if (qse_str_init (&idxstr, MMGR(run), DEF_BUF_CAPA) == QSE_NULL) { @@ -6642,8 +6731,7 @@ static qse_char_t* idxnde_to_str ( return QSE_NULL; } - if (qse_awk_rtx_valtostr ( - run, idx, 0, &idxstr, QSE_NULL) == QSE_NULL) + if (qse_awk_rtx_valtostr (run, idx, &out) == QSE_NULL) { qse_awk_rtx_refdownval (run, idx); qse_str_fini (&idxstr); @@ -7293,6 +7381,8 @@ qse_char_t* qse_awk_rtx_format ( } else { + qse_awk_rtx_valtostr_out_t out; + if (v == val) { qse_awk_rtx_refdownval (run, v); @@ -7300,21 +7390,19 @@ qse_char_t* qse_awk_rtx_format ( return QSE_NULL; } - str = qse_awk_rtx_valtostr ( - run, v, - QSE_AWK_RTX_VALTOSTR_CLEAR, - QSE_NULL, &str_len - ); - if (str == QSE_NULL) + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (run, v, &out) == QSE_NULL) { qse_awk_rtx_refdownval (run, v); return QSE_NULL; } + str = out.u.cpldup.ptr; + str_len = out.u.cpldup.len; str_free = str; } - if (prec == -1 || prec > (qse_long_t)str_len ) prec = (qse_long_t)str_len; + if (prec == -1 || prec > (qse_long_t)str_len) prec = (qse_long_t)str_len; if (prec > width) width = prec; if (!minus) diff --git a/qse/lib/awk/std.c b/qse/lib/awk/std.c index 148ed322..7bfa94b5 100644 --- a/qse/lib/awk/std.c +++ b/qse/lib/awk/std.c @@ -1,5 +1,5 @@ /* - * $Id: std.c 86 2009-02-26 12:55:05Z hyunghwan.chung $ + * $Id: std.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -1268,8 +1268,7 @@ static int fnc_system (qse_awk_rtx_t* run, const qse_char_t* fnm, qse_size_t fnl } else { - str = qse_awk_rtx_valtostr ( - run, v, QSE_AWK_RTX_VALTOSTR_CLEAR, QSE_NULL, &len); + str = qse_awk_rtx_valtostrdup (run, v, &len); if (str == QSE_NULL) return -1; } diff --git a/qse/lib/awk/val.c b/qse/lib/awk/val.c index 2dd3197b..35af2921 100644 --- a/qse/lib/awk/val.c +++ b/qse/lib/awk/val.c @@ -1,5 +1,5 @@ /* - * $Id: val.c 88 2009-02-28 08:44:21Z hyunghwan.chung $ + * $Id: val.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -1129,6 +1129,18 @@ qse_char_t* qse_awk_rtx_valtostr ( return QSE_NULL; } +qse_char_t* qse_awk_rtx_valtostrdup ( + qse_awk_rtx_t* rtx, qse_awk_val_t* v, qse_size_t* len) +{ + qse_awk_rtx_valtostr_out_t out; + + out.type = QSE_AWK_RTX_VALTOSTR_CPLDUP; + if (qse_awk_rtx_valtostr (rtx, v, &out) == QSE_NULL) return QSE_NULL; + + *len = out.u.cpldup.len; + return out.u.cpldup.ptr; +} + int qse_awk_rtx_valtonum ( qse_awk_rtx_t* run, qse_awk_val_t* v, qse_long_t* l, qse_real_t* r) { diff --git a/qse/test/awk/awk03.c b/qse/test/awk/awk03.c index e7162a65..6c3a0e09 100644 --- a/qse/test/awk/awk03.c +++ b/qse/test/awk/awk03.c @@ -1,5 +1,5 @@ /* - * $Id: awk03.c 86 2009-02-26 12:55:05Z hyunghwan.chung $ + * $Id: awk03.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -92,8 +92,8 @@ int main () for (i = 0; i < QSE_COUNTOF(fnc); i++) { qse_awk_val_t* v; - qse_char_t buf[1000]; - qse_size_t bufsize; + qse_char_t* str; + qse_size_t len; v = qse_awk_rtx_call (rtx, fnc[i], QSE_NULL, 0); if (v == QSE_NULL) @@ -103,10 +103,16 @@ int main () ret = -1; goto oops; } - bufsize = QSE_COUNTOF(buf); - qse_awk_rtx_valtostr (rtx, v, - QSE_AWK_RTX_VALTOSTR_FIXED, buf, &bufsize); - qse_printf (QSE_T("return: [%.*s]\n"), (int)bufsize, buf); + str = qse_awk_rtx_valtostrdup (rtx, v, &len); + if (str == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), + qse_awk_rtx_geterrmsg(rtx)); + ret = -1; goto oops; + } + + qse_printf (QSE_T("return: [%.*s]\n"), (int)len, str); + qse_awk_rtx_free (rtx, str); /* clear the return value */ qse_awk_rtx_refdownval (rtx, v); diff --git a/qse/test/awk/awk04.c b/qse/test/awk/awk04.c index 3b38fa0d..8e17585d 100644 --- a/qse/test/awk/awk04.c +++ b/qse/test/awk/awk04.c @@ -1,5 +1,5 @@ /* - * $Id: awk04.c 86 2009-02-26 12:55:05Z hyunghwan.chung $ + * $Id: awk04.c 89 2009-02-28 15:27:03Z hyunghwan.chung $ * Copyright 2006-2009 Chung, Hyung-Hwan. @@ -37,8 +37,8 @@ int main () qse_awk_t* awk = QSE_NULL; qse_awk_rtx_t* rtx = QSE_NULL; qse_awk_parsestd_in_t psin; - qse_char_t buf[1000]; - qse_size_t bufsize; + qse_char_t* str; + qse_size_t len; qse_awk_val_t* v; qse_awk_val_t* arg[2] = { QSE_NULL, QSE_NULL }; int ret, i; @@ -105,10 +105,16 @@ int main () ret = -1; goto oops; } - bufsize = QSE_COUNTOF(buf); - qse_awk_rtx_valtostr (rtx, v, - QSE_AWK_RTX_VALTOSTR_FIXED, buf, &bufsize); - qse_printf (QSE_T("[%.*s]\n"), (int)bufsize, buf); + str = qse_awk_rtx_valtostrdup (rtx, v, &len); + if (str == QSE_NULL) + { + qse_fprintf (QSE_STDERR, QSE_T("error: %s\n"), + qse_awk_rtx_geterrmsg(rtx)); + ret = -1; goto oops; + } + + qse_printf (QSE_T("[%.*s]\n"), (int)len, str); + qse_awk_rtx_free (rtx, str); /* clear the return value */ qse_awk_rtx_refdownval (rtx, v);