LCOV - code coverage report
Current view: top level - tests - tld_test.c (source / functions) Coverage Total Hit
Test: coverage.info Lines: 61.0 % 300 183
Test Date: 2025-07-17 21:03:15 Functions: 100.0 % 9 9
Legend: Lines: hit not hit

            Line data    Source code
       1              : /* TLD library -- test the TLD interface
       2              :  * Copyright (c) 2011-2023  Made to Order Software Corp.  All Rights Reserved
       3              :  *
       4              :  * Permission is hereby granted, free of charge, to any person obtaining a
       5              :  * copy of this software and associated documentation files (the
       6              :  * "Software"), to deal in the Software without restriction, including
       7              :  * without limitation the rights to use, copy, modify, merge, publish,
       8              :  * distribute, sublicense, and/or sell copies of the Software, and to
       9              :  * permit persons to whom the Software is furnished to do so, subject to
      10              :  * the following conditions:
      11              :  *
      12              :  * The above copyright notice and this permission notice shall be included
      13              :  * in all copies or substantial portions of the Software.
      14              :  *
      15              :  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
      16              :  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
      17              :  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
      18              :  * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
      19              :  * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
      20              :  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
      21              :  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
      22              :  */
      23              : 
      24              : /** \file
      25              :  * \brief Test the tld() function like an end user.
      26              :  *
      27              :  * This file implements various tests verifying the tld() function.
      28              :  * The tests defined here are not for coverage but rather edge
      29              :  * cases which could be hard to expect in a full coverage test.
      30              :  */
      31              : 
      32              : // libtld
      33              : //
      34              : #include    <libtld/tld.h>
      35              : #include    <libtld/tld_data.h>
      36              : #include    <libtld/tld_file.h>
      37              : 
      38              : 
      39              : // C
      40              : //
      41              : #include    <string.h>
      42              : #include    <stdlib.h>
      43              : #include    <stdio.h>
      44              : #include    <limits.h>
      45              : 
      46              : 
      47              : 
      48              : 
      49              : 
      50              : 
      51              : int err_count = 0;
      52              : int verbose = 0;
      53              : 
      54              : /*
      55              :  * This test calls the tld() function with all the TLDs and then
      56              :  * with wrong TLDs to make sure that the tld() functions works as
      57              :  * expected.
      58              :  *
      59              :  * extern enum tld_result tld(const char *uri, struct tld_info *info);
      60              :  */
      61              : 
      62              : 
      63              : char *              g_filename1 = "../../BUILD/Debug/contrib/libtld/libtld/tlds.tld";
      64              : char *              g_filename2 = "../libtld/tlds.tld";
      65              : struct tld_file *   g_tld_file = NULL;
      66              : 
      67              : 
      68              : /* we get access to the table with all the TLDs so we can go through them all
      69              :  * the library does not give direct access by default... (although maybe we
      70              :  * could give users access to the data)
      71              :  */
      72            1 : void load_tlds()
      73              : {
      74              :     enum tld_file_error err;
      75              : 
      76            1 :     err = tld_file_load(g_filename1, &g_tld_file);
      77            1 :     if(err == TLD_FILE_ERROR_NONE)
      78              :     {
      79            1 :         return;
      80              :     }
      81              : 
      82            0 :     err = tld_file_load(g_filename2, &g_tld_file);
      83            0 :     if(err == TLD_FILE_ERROR_NONE)
      84              :     {
      85            0 :         return;
      86              :     }
      87              : 
      88            0 :     fprintf(stderr, "fatal error: could not read TLD files \"%s\" or \"%s\".\n",
      89              :                         g_filename1, g_filename2);
      90            0 :     exit(1);
      91              : }
      92              : 
      93              : 
      94            1 : void free_tlds()
      95              : {
      96            1 :     tld_file_free(&g_tld_file);
      97            1 : }
      98              : 
      99              : 
     100              : /** \brief Build an extension from any offset.
     101              :  *
     102              :  * Create a domain name extensions from any entry in the TLD
     103              :  * descriptions.
     104              :  *
     105              :  * \param[in] offset  The offset in the tld_descriptions table
     106              :  * \param[in] uri  The URI buffer
     107              :  *
     108              :  * \return true if the first TLD is a star ("*").
     109              :  */
     110        59920 : int cat_ext(int offset, char * uri)
     111              : {
     112              :     int                             o, has_star;
     113        59920 :     uint32_t                        k, l;
     114              :     struct tld_description const *  tld;
     115              :     char const *                    name;
     116        59920 :     char *                          d = uri;
     117              : 
     118      1998250 :     while(*d != '\0')
     119              :     {
     120      1938330 :         ++d;
     121              :     }
     122              : 
     123        59920 :     tld = tld_file_description(g_tld_file, offset);
     124        59920 :     name = tld_file_string(g_tld_file, tld->f_tld, &l);
     125              : 
     126              :     // verify that the names do match between the library TLDs file and
     127              :     // our copy of the file
     128              :     {
     129        59920 :         struct tld_file const * lib_tld = tld_get_tlds();
     130        59920 :         tld = tld_file_description(lib_tld, offset);
     131        59920 :         uint32_t length = 2000;
     132        59920 :         char const * name2 = tld_file_string(lib_tld, tld->f_tld, &length);
     133        59920 :         if(l != length || memcmp(name, name2, l) != 0)
     134              :         {
     135            0 :             fprintf(stderr, "error: the names in our and the library files do not match: [%.*s] vs [%.*s]\n",
     136              :                             l, name, length, name2);
     137            0 :             abort();
     138              :         }
     139              :     }
     140              : 
     141        59920 :     has_star = l == 1 && name[0] == '*';
     142              : 
     143        59920 :     if(!has_star)
     144              :     {
     145        59110 :         *d++ = '.';
     146       460270 :         for(; *name != '\0' && l > 0; --l)
     147              :         {
     148       401160 :             *d++ = *name++;
     149              :         }
     150              :         //strcat(uri, ".");
     151              :         //strncat(uri, name, l);
     152              :     }
     153        59920 :     o = offset;
     154    662052290 :     for(k = offset + 1; k < g_tld_file->f_descriptions_count; ++k)
     155              :     {
     156    661992370 :         tld = tld_file_description(g_tld_file, k);
     157    661992370 :         if(o >= tld->f_start_offset
     158     60325135 :         && o < tld->f_end_offset)
     159              :         {
     160              :             /* found a parent */
     161        76140 :             name = tld_file_string(g_tld_file, tld->f_tld, &l);
     162        76140 :             if(l != 1 || name[0] != '*')
     163              :             {
     164        76140 :                 *d++ = '.';
     165       392505 :                 for(; *name != '\0' && l > 0; --l)
     166              :                 {
     167       316365 :                     *d++ = *name++;
     168              :                 }
     169              :             }
     170              :             else
     171              :             {
     172            0 :                 fprintf(stderr, "fatal error: found \"*\" at the wrong place; it's only supported as the very first segment.\n");
     173            0 :                 exit(1);
     174              :             }
     175        76140 :             o = k;
     176        76140 :             k = tld->f_end_offset;
     177              :         }
     178              :     }
     179              : 
     180        59920 :     *d = '\0';
     181              : 
     182        59920 :     return has_star;
     183              : }
     184              : 
     185              : 
     186              : 
     187              : 
     188              : struct test_uris
     189              : {
     190              :     const char *        f_uri;
     191              :     enum tld_result     f_result;
     192              :     int                 f_offset;
     193              : };
     194              : 
     195              : 
     196              : const struct test_uris g_uris[] =
     197              : {
     198              :     {
     199              :         "advisor-z2-ngprod-1997768525.us-west-2.elb.amazonaws.com",
     200              :         TLD_RESULT_SUCCESS,
     201              :         28,
     202              :     },
     203              :     {
     204              :         "us-west-2.elb.amazonaws.com",
     205              :         TLD_RESULT_SUCCESS,
     206              :         0,
     207              :     },
     208              :     {
     209              :         "m2osw.com",
     210              :         TLD_RESULT_SUCCESS,
     211              :         5,
     212              :     },
     213              :     {
     214              :         ".com",
     215              :         TLD_RESULT_SUCCESS,
     216              :         0,
     217              :     },
     218              :     {
     219              :         "com",
     220              :         TLD_RESULT_NO_TLD,
     221              :         -1,
     222              :     },
     223              :     {
     224              :         ".ar",
     225              :         TLD_RESULT_SUCCESS,
     226              :         0,
     227              :     },
     228              :     {
     229              :         "int.ar",
     230              :         TLD_RESULT_SUCCESS,
     231              :         0,
     232              :     },
     233              :     {
     234              :         "blah.int.ar",
     235              :         TLD_RESULT_SUCCESS,
     236              :         4,
     237              :     },
     238              :     {
     239              :         "orange.blah.int.ar",
     240              :         TLD_RESULT_SUCCESS,
     241              :         11,
     242              :     },
     243              :     {
     244              :         "congresodelalengua3.ar",   /* congresodelalengua3 is an exceptional 2nd level */
     245              :         TLD_RESULT_SUCCESS,
     246              :         19,
     247              :     },
     248              :     {
     249              :         "special.congresodelalengua3.ar",   /* congresodelalengua3 is an exceptional 2nd level */
     250              :         TLD_RESULT_SUCCESS,
     251              :         27,
     252              :     },
     253              :     {
     254              :         "night-club.kawasaki.jp",
     255              :         TLD_RESULT_SUCCESS,
     256              :         0,
     257              :     },
     258              :     {
     259              :         "orange.night-club.kawasaki.jp",
     260              :         TLD_RESULT_SUCCESS,
     261              :         6,
     262              :     },
     263              : };
     264              : 
     265              : 
     266              : /*
     267              :  * This tests various ad hoc domains with expected results.
     268              :  *
     269              :  * This way we can verify specific things we want to check.
     270              :  */
     271            1 : void test_specific()
     272              : {
     273           14 :     for(size_t idx = 0; idx < sizeof(g_uris) / sizeof(g_uris[0]); ++idx)
     274              :     {
     275           13 :         struct tld_info info;
     276           13 :         enum tld_result r = tld(g_uris[idx].f_uri, &info);
     277           13 :         if(verbose)
     278              :         {
     279            0 :             fprintf(
     280              :                   stderr
     281              :                 , "info: URI \"%s\" returned %d and TLD is \"%s\"\n"
     282            0 :                 , g_uris[idx].f_uri
     283              :                 , r
     284            0 :                 , g_uris[idx].f_uri + info.f_offset);
     285              :         }
     286              : 
     287           13 :         if(r != g_uris[idx].f_result)
     288              :         {
     289            0 :             fprintf(stderr, "error: testing URI \"%s\" got result %d, expected %d and TLD of \"%s\"\n",
     290            0 :                         g_uris[idx].f_uri, r, g_uris[idx].f_result,
     291            0 :                         g_uris[idx].f_uri + g_uris[idx].f_offset);
     292            0 :             ++err_count;
     293              :         }
     294           13 :         else if(info.f_offset != g_uris[idx].f_offset)
     295              :         {
     296            0 :             fprintf(stderr, "error: testing URI \"%s\" got offset %d, expected %d and TLD of \"%s\"\n",
     297            0 :                         g_uris[idx].f_uri, info.f_offset, g_uris[idx].f_offset,
     298            0 :                         g_uris[idx].f_uri + info.f_offset);
     299            0 :             ++err_count;
     300              :         }
     301              :     }
     302            1 : }
     303              : 
     304              : 
     305              : /*
     306              :  * This test goes through all the domain names and extracts the domain,
     307              :  * sub-domains and TLDs. (Or at least verifies that we get the correct
     308              :  * information in order to do so.)
     309              :  *
     310              :  * It builds a URI with zero to many sub-domain names, adds a specific
     311              :  * domain name, then append a complete TLD. The result is then checked
     312              :  * with the tld() function from the library. The tld() is expected to
     313              :  * either return VALID or INVALID but nothing else (since all those
     314              :  * TLDs exist in our table.) Then we verify that the returned offset is
     315              :  * a perfect match.
     316              :  */
     317            1 : void test_all()
     318              : {
     319            1 :     char const * sub_domains[] = {
     320              :         "",
     321              :         "www.",
     322              :         "tld.",
     323              :         "george.snap.",
     324              :         "very.long.sub.domain.ext.en.sion.here."
     325              :         "host.%20.space."
     326              :         "host.%fa.u-acute."
     327              :         "host.%FA.U-acute."
     328              :     };
     329            1 :     struct tld_info                 info;
     330            1 :     char                            uri[256], extension_uri[256];
     331              :     char const *                    name;
     332            1 :     uint32_t                        i, j, l, p, max_subdomains;
     333              :     int                             has_star, sub_has_star;
     334              :     enum tld_result                 r;
     335              :     struct tld_description const  * tld_desc;
     336              :     struct tld_description const  * sub_tld;
     337              : 
     338            1 :     max_subdomains = sizeof(sub_domains) / sizeof(sub_domains[0]);
     339              : 
     340        11966 :     for(i = 0; i < g_tld_file->f_descriptions_count; ++i)
     341              :     {
     342        71790 :         for(j = 0; j < max_subdomains; ++j)
     343              :         {
     344        59825 :             strcpy(uri, sub_domains[j]);
     345        59825 :             strcat(uri, "domain-name");
     346        59825 :             has_star = cat_ext(i, uri);
     347              : 
     348              :             /* just in case make sure that we did not overflow the buffer */
     349        59825 :             if(strlen(uri) >= sizeof(uri))
     350              :             {
     351            0 :                 fprintf(stderr, "fatal error: the URI \"%s\" is longer than the uri[] array.\n", uri);
     352            0 :                 exit(1);
     353              :             }
     354              : 
     355              :             /* reset the structure so we can verify it gets initialized */
     356        59825 :             memset(&info, 0xFE, sizeof(info));
     357              : 
     358        59825 :             r = tld(uri, &info);
     359              : #if 0
     360              :             if(i == 5108)
     361              :             {
     362              :                 for(size_t l = 0; l < sizeof(info); ++l)
     363              :                 {
     364              :                     if((l % 16) == 0 && l > 0)
     365              :                     {
     366              :                         fprintf(stderr, "\n");
     367              :                     }
     368              :                     fprintf(stderr, "0x%02X ", ((unsigned char*)&info)[l]);
     369              :                 }
     370              :                 fprintf(stderr, "\nresult for [%s]: category[%d], status[%d/%%d n.a.], country[%s],"
     371              :                                     " tld[%s], offset[%d]\n",
     372              :                         uri,
     373              :                         (int)info.f_category,
     374              :                         (int)info.f_status, //(int)tld_descriptions[i].f_status,
     375              :                         info.f_country,
     376              :                             info.f_tld, (int)info.f_offset);
     377              :             }
     378              : #endif
     379        59825 :             p = i;
     380        59825 :             tld_desc = tld_file_description(g_tld_file, i);
     381        59825 :             if(tld_desc->f_status == TLD_STATUS_EXCEPTION)
     382              :             {
     383           95 :                 if(tld_desc->f_exception_apply_to == USHRT_MAX)
     384              :                 {
     385            0 :                     fprintf(stderr, "error: domain name for \"%s\" (%d) is said to be an exception but it has no apply-to parameter. (result: %d)\n",
     386              :                             uri, i, r);
     387            0 :                     ++err_count;
     388              :                 }
     389              :                 else
     390              :                 {
     391           95 :                     p = tld_desc->f_exception_apply_to;
     392              :                 }
     393              :             }
     394        59825 :             if(tld_desc->f_status == TLD_STATUS_VALID)
     395              :             {
     396        48975 :                 if(r != TLD_RESULT_SUCCESS)
     397              :                 {
     398            0 :                     fprintf(stderr, "error: valid domain name for \"%s\" (%d) could not be extracted successfully (returned: %d)\n",
     399              :                             uri, i, r);
     400            0 :                     ++err_count;
     401              :                 }
     402        48975 :                 else if(has_star)
     403              :                 {
     404              :                     /* the "domain-name" is absorbed as part of the TLD */
     405          810 :                     int expected = strlen(sub_domains[j]);
     406          810 :                     if(expected != 0)
     407              :                     {
     408          648 :                         --expected;     /* ignore the "." */
     409              :                     }
     410          810 :                     if(info.f_offset != expected)
     411              :                     {
     412            0 :                         fprintf(stderr, "error: valid domain name for \"%s\" (%d) could not be extracted successfully (offset: %d, expected: %d)\n",
     413              :                                 uri, i,
     414              :                                 info.f_offset, expected);
     415            0 :                         ++err_count;
     416              :                     }
     417              :                 }
     418              :                 else
     419              :                 {
     420              :                     /* verify the top domain name */
     421        48165 :                     if(info.f_offset < 11)
     422              :                     {
     423            0 :                         fprintf(stderr, "error: somehow the top domain name in \"%s\" (%d) cannot properly be extracted\n",
     424              :                                 uri, i);
     425            0 :                         ++err_count;
     426              :                     }
     427        48165 :                     else if(strncmp(uri + info.f_offset - 11, "domain-name", 11) != 0)
     428              :                     {
     429            0 :                         fprintf(stderr, "error: valid domain name for \"%s\" (%d) could not be extracted successfully (offset: %d)\n",
     430              :                                 uri, i, info.f_offset);
     431            0 :                         ++err_count;
     432              :                     }
     433              :                     /*
     434              :                     else
     435              :                         fprintf(stderr, "valid: \"%s\" -> \"%s\"\n", uri, info.f_tld);
     436              :                     */
     437              :                 }
     438              :             }
     439        10850 :             else if(tld_desc->f_status == TLD_STATUS_EXCEPTION)
     440              :             {
     441           95 :                 if(r != TLD_RESULT_SUCCESS)
     442              :                 {
     443            0 :                     fprintf(stderr, "error: exceptional domain name for \"%s\" (%d) could not be extracted successfully (returned: %d)\n",
     444              :                             uri, i, r);
     445            0 :                     ++err_count;
     446              :                 }
     447              :                 else
     448              :                 {
     449           95 :                     extension_uri[0] = '\0';
     450           95 :                     cat_ext(p, extension_uri);
     451           95 :                     if(strcmp(info.f_tld, extension_uri) != 0)
     452              :                     //if(strncmp(uri + info.f_offset - 11, "domain-name", 11) != 0)
     453              :                     {
     454            0 :                         fprintf(stderr, "error: exceptional domain name for \"%s\" (%d/%d) could not be extracted successfully as \"%s\" (offset: %d)\n",
     455              :                                 uri, i, p, extension_uri, info.f_offset);
     456            0 :                         ++err_count;
     457              :                     }
     458              :                     /*
     459              :                     else
     460              :                         fprintf(stderr, "valid: \"%s\" -> \"%s\"\n", uri, info.f_tld);
     461              :                     */
     462              :                 }
     463              :             }
     464              :             else
     465              :             {
     466        10755 :                 sub_has_star = 0;
     467        10755 :                 if(tld_desc->f_status == TLD_STATUS_UNUSED
     468         3125 :                 && tld_desc->f_start_offset != USHRT_MAX)
     469              :                 {
     470         2780 :                     sub_tld = tld_file_description(g_tld_file, tld_desc->f_start_offset);
     471         2780 :                     name = tld_file_string(g_tld_file, sub_tld->f_tld, &l);
     472         2780 :                     sub_has_star = l == 1 && name[0] == '*';
     473              :                 }
     474        10755 :                 if(sub_has_star)
     475              :                 {
     476              :                     /* this is a special case, an entry such as:
     477              :                      *
     478              :                      *     *.blah.com
     479              :                      *
     480              :                      * and that means the result is going to be SUCCESS
     481              :                      * and VALID...
     482              :                      */
     483          810 :                     if(r != TLD_RESULT_SUCCESS
     484          810 :                     || info.f_status != TLD_STATUS_VALID)
     485              :                     {
     486            0 :                         fprintf(stderr, "error: domain name for \"%s\" (%d) could not be extracted as expected (returned: %d) [1]\n",
     487              :                                 uri, i, r);
     488            0 :                         ++err_count;
     489              :                     }
     490              :                 }
     491         9945 :                 else if(r != TLD_RESULT_INVALID)
     492              :                 {
     493            0 :                     fprintf(stderr, "error: domain name for \"%s\" (%d) could not be extracted as expected (returned: %d) [2]\n",
     494              :                             uri, i, r);
     495            0 :                     ++err_count;
     496              :                 }
     497         9945 :                 else if(p != i)
     498              :                 {
     499            0 :                     extension_uri[0] = '\0';
     500            0 :                     cat_ext(p, extension_uri);
     501            0 :                     if(strcmp(info.f_tld, extension_uri) != 0)
     502              :                     {
     503            0 :                         fprintf(stderr, "error: other domain name for \"%s\" (%d) could not be extracted successfully (returned: %d/%s != %s) [1]\n",
     504              :                                 uri, i, r, info.f_tld, extension_uri);
     505            0 :                         ++err_count;
     506              :                     }
     507              :                     /*
     508              :                     else
     509              :                         fprintf(stderr, "?? invalid: \"%s\" -> \"%s\"\n", uri, info.f_tld); 
     510              :                     */
     511              :                 }
     512              :                 else
     513              :                 {
     514         9945 :                     if(strncmp(uri + info.f_offset - 11, "domain-name", 11) != 0)
     515              :                     {
     516            0 :                         fprintf(stderr, "error: other domain name for \"%s\" (%d) could not be extracted successfully (returned: %d/%s) [2]\n",
     517              :                                 uri, i, r, info.f_tld);
     518            0 :                         ++err_count;
     519              :                     }
     520              :                     /*
     521              :                     else
     522              :                         fprintf(stderr, "?? invalid: \"%s\" -> \"%s\"\n", uri, info.f_tld); 
     523              :                     */
     524              :                 }
     525              :             }
     526              :         }
     527              :     }
     528            1 : }
     529              : 
     530              : 
     531              : /*
     532              :  * This test checks out URIs that end with an invalid TLD. This is
     533              :  * expected to return an error every single time.
     534              :  */
     535            1 : void test_unknown()
     536              : {
     537              :     struct bad_data
     538              :     {
     539              :         const char *        f_uri;
     540              :     };
     541            1 :     struct bad_data d[] =
     542              :     {
     543              :         { "this.is.wrong" },
     544              :         { "missing.tld" },
     545              :         { ".net.absolutely.com.no.info.on.this" }
     546              :     };
     547            1 :     struct tld_info info;
     548              :     int i, max;
     549              :     enum tld_result r;
     550              : 
     551            1 :     max = sizeof(d) / sizeof(d[0]);
     552            4 :     for(i = 0; i < max; ++i)
     553              :     {
     554            3 :         memset(&info, 0xFE, sizeof(info));
     555            3 :         r = tld(d[i].f_uri, &info);
     556            3 :         if(r != TLD_RESULT_NOT_FOUND)
     557              :         {
     558            0 :             fprintf(stderr, "error: the invalid URI \"%s\" was found by tld()!\n", d[i].f_uri);
     559            0 :             ++err_count;
     560              :         }
     561              :     }
     562            1 : }
     563              : 
     564              : 
     565              : 
     566              : 
     567            1 : void test_invalid()
     568              : {
     569            1 :     struct tld_info undefined_info;
     570            1 :     struct tld_info clear_info;
     571            1 :     struct tld_info info;
     572              :     enum tld_result r;
     573              : 
     574              :     /*
     575              :      * We reset the undefined_info the same way we reset the info
     576              :      * structure because the alignment on 64bits may add another
     577              :      * 4 bytes at the end of the structure that are not otherwise
     578              :      * accessible.
     579              :      */
     580            1 :     memset(&undefined_info, 0xFE, sizeof(undefined_info));
     581            1 :     undefined_info.f_category  = TLD_CATEGORY_UNDEFINED;
     582            1 :     undefined_info.f_status    = TLD_STATUS_UNDEFINED;
     583            1 :     memset(undefined_info.f_country, 0, sizeof(undefined_info.f_country));
     584            1 :     undefined_info.f_tld       = (const char *) 0;
     585            1 :     undefined_info.f_offset    = -1;
     586            1 :     undefined_info.f_tld_index = -1;
     587              : 
     588            1 :     memset(&clear_info, 0xFE, sizeof(clear_info));
     589              : 
     590              :     /* test: NULL */
     591            1 :     info = clear_info;
     592            1 :     r = tld(NULL, &info);
     593            1 :     if(r != TLD_RESULT_NULL)
     594              :     {
     595            0 :         fprintf(stderr, "error: the NULL URI did not return the TLD_RESULT_NULL result.\n");
     596            0 :         ++err_count;
     597              :     }
     598            1 :     if(memcmp(&info, &undefined_info, sizeof(info)) != 0)
     599              :     {
     600            0 :         fprintf(stderr, "error: the NULL URI did not return a reset info structure.\n");
     601            0 :         ++err_count;
     602              :     }
     603              : 
     604              :     /* test: "" */
     605            1 :     info = clear_info;
     606            1 :     r = tld("", &info);
     607            1 :     if(r != TLD_RESULT_NULL)
     608              :     {
     609            0 :         fprintf(stderr, "error: the \"\" URI did not return the TLD_RESULT_NULL result.\n");
     610            0 :         ++err_count;
     611              :     }
     612            1 :     if(memcmp(&info, &undefined_info, sizeof(info)) != 0)
     613              :     {
     614            0 :         fprintf(stderr, "error: the \"\" URI did not return a reset info structure.\n");
     615            0 :         ++err_count;
     616              :     }
     617              : 
     618              :     /* test: ".." (two periods one after another) */
     619            1 :     info = clear_info;
     620            1 :     r = tld("test..com", &info);
     621            1 :     if(r != TLD_RESULT_BAD_URI)
     622              :     {
     623            0 :         fprintf(stderr, "error: the \"test..com\" URI did not return the TLD_RESULT_BAD_URI result.\n");
     624            0 :         ++err_count;
     625              :     }
     626            1 :     if(memcmp(&info, &undefined_info, sizeof(info)) != 0)
     627              :     {
     628            0 :         fprintf(stderr, "error: the \"test..com\" URI did not return a reset info structure.\n");
     629            0 :         ++err_count;
     630              :     }
     631              : 
     632              :     /* test: ".." (two periods one after another) */
     633            1 :     info = clear_info;
     634            1 :     r = tld("more..test.com", &info);
     635            1 :     if(r != TLD_RESULT_BAD_URI)
     636              :     {
     637            0 :         fprintf(stderr, "error: the \"more..test.com\" URI did not return the TLD_RESULT_BAD_URI result.\n");
     638            0 :         ++err_count;
     639              :     }
     640            1 :     if(memcmp(&info, &undefined_info, sizeof(info)) != 0)
     641              :     {
     642            0 :         fprintf(stderr, "error: the \"more..test.com\" URI did not return a reset info structure.\n");
     643            0 :         ++err_count;
     644              :     }
     645              : 
     646              :     /* test: "noperiodanywhere" (no periods anywhere) */
     647            1 :     info = clear_info;
     648            1 :     r = tld("noperiodanywhere", &info);
     649            1 :     if(r != TLD_RESULT_NO_TLD)
     650              :     {
     651            0 :         fprintf(stderr, "error: the \"noperiodanywhere\" URI did not return the TLD_RESULT_NO_TLD result.\n");
     652            0 :         ++err_count;
     653              :     }
     654            1 :     if(memcmp(&info, &undefined_info, sizeof(info)) != 0)
     655              :     {
     656            0 :         fprintf(stderr, "error: the \"noperiodanywhere\" URI did not return a reset info structure.\n");
     657            0 :         ++err_count;
     658              :     }
     659            1 : }
     660              : 
     661              : 
     662            1 : void test_tags()
     663              : {
     664            1 :     struct tld_info info;
     665              :     enum tld_result result;
     666            1 :     const char * tld_name = "info.%e6%be%b3%e9%96%80";
     667              :     int tag_count;
     668            1 :     struct tld_tag_definition tag_info;
     669              : 
     670            1 :     result = tld(tld_name, &info);
     671            1 :     if(result != TLD_RESULT_SUCCESS)
     672              :     {
     673            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI did not return a valid info structure (error: %d).\n",
     674              :                 result);
     675            0 :         ++err_count;
     676            0 :         return;
     677              :     }
     678              : 
     679            1 :     if(info.f_status != TLD_STATUS_VALID)
     680              :     {
     681            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI did not return a VALID status as expected.\n");
     682            0 :         ++err_count;
     683            0 :         return;
     684              :     }
     685              : 
     686            1 :     if(info.f_category != TLD_CATEGORY_COUNTRY)
     687              :     {
     688            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI did not return a country category as expected, got %d instead.\n",
     689            0 :                         info.f_category);
     690            0 :         ++err_count;
     691            0 :         return;
     692              :     }
     693              : 
     694            1 :     if(strcmp(info.f_country, "Macao") != 0)
     695              :     {
     696            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI did not return \"Macao\" as the country name.\n");
     697            0 :         ++err_count;
     698            0 :         return;
     699              :     }
     700              : 
     701            1 :     if(info.f_tld != tld_name + 4)
     702              :     {
     703            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI did not return the expected f_tld pointer.\n");
     704            0 :         ++err_count;
     705            0 :         return;
     706              :     }
     707              : 
     708            1 :     if(info.f_offset != 4)
     709              :     {
     710            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI did not return the expected f_offset.\n");
     711            0 :         ++err_count;
     712            0 :         return;
     713              :     }
     714              : 
     715              :     // info.f_tld_index -- we assume this will change, there is no real point
     716              :     //                     in testing this specifically
     717              : 
     718            1 :     tag_count = tld_tag_count(&info);
     719            1 :     if(tag_count < 0)
     720              :     {
     721            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI returned a negative tag_count.\n");
     722            0 :         ++err_count;
     723            0 :         return;
     724              :     }
     725            1 :     if(tag_count != 6)
     726              :     {
     727            0 :         fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI was expected to have 6 tags. Edit test if new tags were added.\n");
     728            0 :         ++err_count;
     729              :     }
     730              : 
     731            7 :     for(int idx = 0; idx < tag_count; ++idx)
     732              :     {
     733            6 :         result = tld_get_tag(&info, idx, &tag_info);
     734            6 :         if(result != TLD_RESULT_SUCCESS)
     735              :         {
     736            0 :             fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI returned an error retrieving tag %d.\n", idx);
     737            0 :             ++err_count;
     738            0 :             return;
     739              :         }
     740              : 
     741              :         // the order in which tags are saved in not guaranteed, so we must
     742              :         // test the name and decide what to do next
     743              :         //
     744            6 :         if(tag_info.f_name_length == 7
     745            1 :         && memcmp(tag_info.f_name, "country", 7) == 0)
     746              :         {
     747            1 :             if(tag_info.f_value_length != 5
     748            1 :             || memcmp(tag_info.f_value, "Macao", 5) != 0)
     749              :             {
     750            0 :                 fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI \"country\" name was expected to be \"Macao\".\n");
     751            0 :                 ++err_count;
     752            0 :                 return;
     753              :             }
     754              :         }
     755            5 :         else if(tag_info.f_name_length == 17
     756            1 :              && memcmp(tag_info.f_name, "country_full_name", 17) == 0)
     757              :         {
     758            1 :             if(tag_info.f_value_length != 76
     759            1 :             || memcmp(tag_info.f_value, "Macao Special Administrative Region of the People's Republic of China (MSAR)", 76) != 0)
     760              :             {
     761            0 :                 fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI \"country_full_name\" was expected to be \"Macao Special Administrative Region of the People's Republic of China (MSAR)\".\n");
     762            0 :                 ++err_count;
     763            0 :                 return;
     764              :             }
     765              :         }
     766            4 :         else if(tag_info.f_name_length == 11
     767            1 :              && memcmp(tag_info.f_name, "description", 11) == 0)
     768              :         {
     769            1 :             if(tag_info.f_value_length != 12
     770            1 :             || memcmp(tag_info.f_value, "Macao Island", 12) != 0)
     771              :             {
     772            0 :                 fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI \"description\" was expected to be \"Macao Island\".\n");
     773            0 :                 ++err_count;
     774            0 :                 return;
     775              :             }
     776              :         }
     777            3 :         else if(tag_info.f_name_length == 4
     778            1 :              && memcmp(tag_info.f_name, "note", 4) == 0)
     779              :         {
     780            1 :             if(tag_info.f_value_length != 5
     781            1 :             || memcmp(tag_info.f_value, "Macao", 5) != 0)
     782              :             {
     783            0 :                 fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI \"note\" was expected to be \"Macao\".\n");
     784            0 :                 ++err_count;
     785            0 :                 return;
     786              :             }
     787              :         }
     788            2 :         else if(tag_info.f_name_length == 8
     789            2 :              && memcmp(tag_info.f_name, "language", 8) == 0)
     790              :         {
     791            1 :             if(tag_info.f_value_length != 20
     792            1 :             || memcmp(tag_info.f_value, "Chinese, Traditional", 20) != 0)
     793              :             {
     794            0 :                 fprintf(stderr, "error: the \"info.\xE6\xBE\xB3\xE9\x96\x80\" URI \"language\" was expected to be \"Chinese, Traditional\".\n");
     795            0 :                 ++err_count;
     796            0 :                 return;
     797              :             }
     798              :         }
     799              :     }
     800              : }
     801              : 
     802              : 
     803              : 
     804              : 
     805            1 : int main(int argc, char *argv[])
     806              : {
     807            1 :     fprintf(stderr, "testing tld version %s\n", tld_version());
     808              : 
     809            1 :     if(argc > 1)
     810              :     {
     811            0 :         if(strcmp(argv[1], "-v") == 0)
     812              :         {
     813            0 :             verbose = 1;
     814              :         }
     815              :         else
     816              :         {
     817            0 :             fprintf(stderr, "error: unknown command line option \"%s\"\n", argv[1]);
     818            0 :             exit(1);
     819              :         }
     820              :     }
     821              : 
     822              :     /* call all the tests, one by one
     823              :      * failures are "recorded" in the err_count global variable
     824              :      * and the process stops with an error message and exit(1)
     825              :      * if err_count is not zero.
     826              :      */
     827            1 :     load_tlds();
     828            1 :     test_specific();
     829            1 :     test_all();
     830            1 :     test_unknown();
     831            1 :     test_invalid();
     832            1 :     test_tags();
     833            1 :     free_tlds();
     834              : 
     835            1 :     if(err_count)
     836              :     {
     837            0 :         fprintf(stderr, "%d error%s occured.\n",
     838            0 :                     err_count, err_count != 1 ? "s" : "");
     839              :     }
     840            1 :     exit(err_count ? 1 : 0);
     841              : }
     842              : 
     843              : /* vim: ts=4 sw=4 et
     844              :  */
        

Generated by: LCOV version 2.0-1

Snap C++ | List of projects | List of versions