Team Ai
Modelpublic

AryaWu/sqlite

sourceHugging Faceupdated 10mo agoView on Hugging Face
0likes
tests_func_printfFunc.c233 linesDownload Raw Back to tests
1#include "sqliteInt.h"2#include "unity.h"3#include <stdlib.h>4#include <string.h>5#include <stdio.h>6 7/* Prototype of the global wrapper provided in the module */8void test_printfFunc(sqlite3_context *context, int argc, sqlite3_value **argv);9 10static sqlite3 *gDb = NULL;11static Vdbe *gVdbe = NULL;12static sqlite3_context gCtx;13static Mem gOut;14 15static Mem* makeText(const char *z){16    Mem *m = sqlite3ValueNew(gDb);17    TEST_ASSERT_NOT_NULL(m);18    /* -1 length means to compute strlen, SQLITE_TRANSIENT so SQLite copies data if needed */19    int rc = sqlite3VdbeMemSetStr(m, z, -1, SQLITE_UTF8, SQLITE_TRANSIENT);20    TEST_ASSERT_EQUAL_INT(SQLITE_OK, rc);21    return m;22}23static Mem* makeInt64(sqlite3_int64 v){24    Mem *m = sqlite3ValueNew(gDb);25    TEST_ASSERT_NOT_NULL(m);26    sqlite3VdbeMemSetInt64(m, v);27    return m;28}29static Mem* makeDouble(double v){30    Mem *m = sqlite3ValueNew(gDb);31    TEST_ASSERT_NOT_NULL(m);32    sqlite3VdbeMemSetDouble(m, v);33    return m;34}35static Mem* makeNull(void){36    Mem *m = sqlite3ValueNew(gDb);37    TEST_ASSERT_NOT_NULL(m);38    sqlite3VdbeMemSetNull(m);39    return m;40}41static void freeVals(int n, Mem **vals){42    for(int i=0;i<n;i++){43        if(vals[i]) sqlite3ValueFree(vals[i]);44    }45}46static void runPrintf(int argc, Mem **argv){47    test_printfFunc(&gCtx, argc, (sqlite3_value**)argv);48}49static const char* resultText(void){50    const unsigned char *z = sqlite3_value_text((sqlite3_value*)&gOut);51    return (const char*)z;52}53 54void setUp(void) {55    int rc = sqlite3_open(":memory:", &gDb);56    TEST_ASSERT_EQUAL_INT(SQLITE_OK, rc);57    gVdbe = sqlite3VdbeCreate(gDb);58    TEST_ASSERT_NOT_NULL(gVdbe);59    memset(&gCtx, 0, sizeof(gCtx));60    memset(&gOut, 0, sizeof(gOut));61    gOut.db = gDb;           /* Ensure output Mem knows the db for allocations */62    gCtx.pVdbe = gVdbe;      /* Needed for sqlite3_context_db_handle() */63    gCtx.pOut = &gOut;       /* Where sqlite3_result_* will store output */64}65 66void tearDown(void) {67    sqlite3VdbeMemRelease(&gOut);68    memset(&gOut, 0, sizeof(gOut));69    if(gVdbe){70        sqlite3VdbeDelete(gVdbe);71        gVdbe = NULL;72    }73    if(gDb){74        sqlite3_close(gDb);75        gDb = NULL;76    }77}78 79/* Tests */80 81void test_printfFunc_literal_no_args(void){82    Mem *fmt = makeText("hello");83    Mem *argv[] = { fmt };84    runPrintf(1, argv);85    const char *got = resultText();86    TEST_ASSERT_NOT_NULL(got);87    TEST_ASSERT_EQUAL_STRING("hello", got);88    freeVals(1, argv);89}90 91void test_printfFunc_integer_decimal(void){92    Mem *fmt = makeText("num=%d");93    Mem *v1 = makeInt64(123);94    Mem *argv[] = { fmt, v1 };95    runPrintf(2, argv);96    const char *got = resultText();97    TEST_ASSERT_NOT_NULL(got);98    TEST_ASSERT_EQUAL_STRING("num=123", got);99    freeVals(2, argv);100}101 102void test_printfFunc_string_basic(void){103    Mem *fmt = makeText("[%s]");104    Mem *v1 = makeText("abc");105    Mem *argv[] = { fmt, v1 };106    runPrintf(2, argv);107    const char *got = resultText();108    TEST_ASSERT_NOT_NULL(got);109    TEST_ASSERT_EQUAL_STRING("[abc]", got);110    freeVals(2, argv);111}112 113void test_printfFunc_float_precision(void){114    Mem *fmt = makeText("%.2f");115    Mem *v1 = makeDouble(3.14159);116    Mem *argv[] = { fmt, v1 };117    runPrintf(2, argv);118    const char *got = resultText();119    TEST_ASSERT_NOT_NULL(got);120    TEST_ASSERT_EQUAL_STRING("3.14", got);121    freeVals(2, argv);122}123 124void test_printfFunc_escaped_percent_and_int(void){125    Mem *fmt = makeText("%%-%d");126    Mem *v1 = makeInt64(7);127    Mem *argv[] = { fmt, v1 };128    runPrintf(2, argv);129    const char *got = resultText();130    TEST_ASSERT_NOT_NULL(got);131    TEST_ASSERT_EQUAL_STRING("%-7", got);132    freeVals(2, argv);133}134 135void test_printfFunc_zero_padded_width(void){136    Mem *fmt = makeText("%06d");137    Mem *v1 = makeInt64(3);138    Mem *argv[] = { fmt, v1 };139    runPrintf(2, argv);140    const char *got = resultText();141    TEST_ASSERT_NOT_NULL(got);142    TEST_ASSERT_EQUAL_STRING("000003", got);143    freeVals(2, argv);144}145 146void test_printfFunc_multiple_mixed_args(void){147    Mem *fmt = makeText("%s %d %.1f");148    Mem *v1 = makeText("a");149    Mem *v2 = makeInt64(2);150    Mem *v3 = makeDouble(3.4);151    Mem *argv[] = { fmt, v1, v2, v3 };152    runPrintf(4, argv);153    const char *got = resultText();154    TEST_ASSERT_NOT_NULL(got);155    TEST_ASSERT_EQUAL_STRING("a 2 3.4", got);156    freeVals(4, argv);157}158 159void test_printfFunc_null_format_results_in_null_output(void){160    /* When the format is NULL, printfFunc does not set a result; output remains NULL */161    Mem *fmt = makeNull();162    Mem *argv[] = { fmt };163    /* Ensure output starts as NULL */164    sqlite3VdbeMemRelease(&gOut);165    memset(&gOut, 0, sizeof(gOut));166    gOut.db = gDb;167 168    runPrintf(1, argv);169    int t = sqlite3_value_type((sqlite3_value*)&gOut);170    TEST_ASSERT_EQUAL_INT(SQLITE_NULL, t);171    freeVals(1, argv);172}173 174void test_printfFunc_percent_Q_sql_quoting(void){175    Mem *fmt = makeText("%Q");176    Mem *v1 = makeText("O'Reilly");177    Mem *argv[] = { fmt, v1 };178    runPrintf(2, argv);179    const char *got = resultText();180    TEST_ASSERT_NOT_NULL(got);181    TEST_ASSERT_EQUAL_STRING("'O''Reilly'", got);182    freeVals(2, argv);183}184 185void test_printfFunc_extra_args_ignored(void){186    Mem *fmt = makeText("X");187    Mem *v1 = makeInt64(999);188    Mem *argv[] = { fmt, v1 };189    runPrintf(2, argv);190    const char *got = resultText();191    TEST_ASSERT_NOT_NULL(got);192    TEST_ASSERT_EQUAL_STRING("X", got);193    freeVals(2, argv);194}195 196void test_printfFunc_large_output(void){197    /* Create a large input string and ensure it passes through */198    const int N = 5000;199    char *big = (char*)sqlite3_malloc(N+1);200    TEST_ASSERT_NOT_NULL(big);201    memset(big, 'x', N);202    big[N] = '\0';203 204    Mem *fmt = makeText("%s");205    Mem *v1 = makeText(big);206    Mem *argv[] = { fmt, v1 };207    runPrintf(2, argv);208    const char *got = resultText();209    TEST_ASSERT_NOT_NULL(got);210    TEST_ASSERT_EQUAL_UINT32((uint32_t)N, (uint32_t)strlen(got));211    /* Spot check: first and last */212    TEST_ASSERT_EQUAL_CHAR('x', got[0]);213    TEST_ASSERT_EQUAL_CHAR('x', got[N-1]);214 215    sqlite3_free(big);216    freeVals(2, argv);217}218 219int main(void){220    UNITY_BEGIN();221    RUN_TEST(test_printfFunc_literal_no_args);222    RUN_TEST(test_printfFunc_integer_decimal);223    RUN_TEST(test_printfFunc_string_basic);224    RUN_TEST(test_printfFunc_float_precision);225    RUN_TEST(test_printfFunc_escaped_percent_and_int);226    RUN_TEST(test_printfFunc_zero_padded_width);227    RUN_TEST(test_printfFunc_multiple_mixed_args);228    RUN_TEST(test_printfFunc_null_format_results_in_null_output);229    RUN_TEST(test_printfFunc_percent_Q_sql_quoting);230    RUN_TEST(test_printfFunc_extra_args_ignored);231    RUN_TEST(test_printfFunc_large_output);232    return UNITY_END();233}