LCOV - code coverage report
Current view: top level - Core/Scripting - OOConstToJSString.m (source / functions) Hit Total Coverage
Test: coverxygen.info Lines: 0 40 0.0 %
Date: 2025-05-28 07:50:54 Functions: 0 0 -

          Line data    Source code
       1           0 : /*
       2             : 
       3             : OOConstToJSString.m
       4             : 
       5             : 
       6             : Oolite
       7             : Copyright (C) 2004-2013 Giles C Williams and contributors
       8             : 
       9             : This program is free software; you can redistribute it and/or
      10             : modify it under the terms of the GNU General Public License
      11             : as published by the Free Software Foundation; either version 2
      12             : of the License, or (at your option) any later version.
      13             : 
      14             : This program is distributed in the hope that it will be useful,
      15             : but WITHOUT ANY WARRANTY; without even the implied warranty of
      16             : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      17             : GNU General Public License for more details.
      18             : 
      19             : You should have received a copy of the GNU General Public License
      20             : along with this program; if not, write to the Free Software
      21             : Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
      22             : MA 02110-1301, USA.
      23             : 
      24             : */
      25             : 
      26             : #include "OOConstToJSString.h"
      27             : 
      28             : 
      29             : /*
      30             :         Each type of constant has its own lookup table, which is a linear list of
      31             :         TableEntry structs plus a count.
      32             :         
      33             :         The list is statically initialized with the constant values and C strings.
      34             :         OOConstToJSStringInit() (through InitTable()) replaces the C strings with
      35             :         interned JSStrings (hence the void * type). These are subsequently
      36             :         constant and no other strings with the same value should occur, i.e. they
      37             :         should be comparable with pointer equality. Because I'm paranoid, we fall
      38             :         back to full string comparison if this fails.
      39             :         
      40             :         ConstTables are globals, which are accessed as local externs in the inlines
      41             :         in the header. All the advantages of globals with most of the advantages
      42             :         of encapsulation, sorta.
      43             :         
      44             :         -- Ahruman 2011-01-15
      45             : */
      46             : 
      47           0 : typedef struct
      48             : {
      49           0 :         NSInteger                       value;
      50           0 :         const char                      *cString;
      51           0 :         JSString                        *jsString;
      52             : } TableEntry;
      53             : 
      54           0 : typedef struct ConstTable
      55             : {
      56           0 :         NSUInteger                      count;
      57           0 :         TableEntry                      *entries;
      58           0 : } ConstTable;
      59             : 
      60           0 : #define TABLE(entries) { sizeof entries / sizeof *entries, entries }
      61             : 
      62             : 
      63           0 : static BOOL sInited = NO;
      64             : 
      65             : /*
      66             :         The interned string "UNDEFINED", returned by OOJSStringFromConstantPRIVATE()
      67             :         if passed a bogus constant value.
      68             : */
      69           0 : static JSString *sUndefinedString;
      70             : 
      71             : 
      72             : /*      
      73             :         Initialize table contents (with C strings, see above) from table files.
      74             : */
      75           0 : #define ENTRY(label, val) { .value = label, .cString = #label },
      76           0 : #define GALACTIC_HYPERSPACE_ENTRY(label, val) { .value = GALACTIC_HYPERSPACE_##label, .cString = #label },
      77           0 : #define DIFF_STRING_ENTRY(label, string) { .value = label, .cString = string },
      78             : 
      79           0 : static TableEntry sOOCompassModeTableEntries[] =
      80             : {
      81             :         #include "OOCompassMode.tbl"
      82             : };
      83             : 
      84           0 : static TableEntry sOOEntityStatusTableEntries[] =
      85             : {
      86             :         #include "OOEntityStatus.tbl"
      87             : };
      88             : 
      89           0 : static TableEntry sOOGalacticHyperspaceBehaviourTableEntries[] =
      90             : {
      91             :         #include "OOGalacticHyperspaceBehaviour.tbl"
      92             : };
      93             : 
      94           0 : static TableEntry sOOGUIScreenIDTableEntries[] =
      95             : {
      96             :         #include "OOGUIScreenID.tbl"
      97             : };
      98             : 
      99           0 : static TableEntry sOOScanClassTableEntries[] =
     100             : {
     101             :         #include "OOScanClass.tbl"
     102             : };
     103             : 
     104           0 : static TableEntry sOOViewIDTableEntries[] =
     105             : {
     106             :         #include "OOViewID.tbl"
     107             : };
     108             : 
     109           0 : static TableEntry sOOShipDamageTypeTableEntries[] =
     110             : {
     111             :         #include "OOShipDamageType.tbl"
     112             : };
     113             : 
     114           0 : static TableEntry sOOLegalStatusReasonTableEntries[] =
     115             : {
     116             :         #include "OOLegalStatusReason.tbl"
     117             : };
     118             : 
     119           0 : static TableEntry sOOLongRangeChartModeTableEntries[] =
     120             : {
     121             :         #include "OOLongRangeChartMode.tbl"
     122             : };
     123             : 
     124             : #undef ENTRY
     125             : #undef GALACTIC_HYPERSPACE_ENTRY
     126             : #undef DIFF_STRING_ENTRY
     127             : 
     128             : 
     129           0 : ConstTable gOOCompassModeConstTable                                     = TABLE(sOOCompassModeTableEntries);
     130           0 : ConstTable gOOEntityStatusConstTable                            = TABLE(sOOEntityStatusTableEntries);
     131           0 : ConstTable gOOGalacticHyperspaceBehaviourConstTable     = TABLE(sOOGalacticHyperspaceBehaviourTableEntries);
     132           0 : ConstTable gOOGUIScreenIDConstTable                                     = TABLE(sOOGUIScreenIDTableEntries);
     133           0 : ConstTable gOOScanClassConstTable                                       = TABLE(sOOScanClassTableEntries);
     134           0 : ConstTable gOOViewIDConstTable                                          = TABLE(sOOViewIDTableEntries);
     135           0 : ConstTable gOOShipDamageTypeConstTable                          = TABLE(sOOShipDamageTypeTableEntries);
     136           0 : ConstTable gOOLegalStatusReasonConstTable                       = TABLE(sOOLegalStatusReasonTableEntries);
     137           0 : ConstTable gOOLongRangeChartModeConstTable                      = TABLE(sOOLongRangeChartModeTableEntries);
     138             : 
     139             : static void InitTable(JSContext *context, ConstTable *table);
     140             : 
     141             : 
     142             : // MARK: Initialization
     143             : 
     144           0 : void OOConstToJSStringInit(JSContext *context)
     145             : {
     146             :         NSCAssert(!sInited, @"OOConstToJSStringInit() called while already inited.");
     147             :         NSCParameterAssert(context != NULL && JS_IsInRequest(context));
     148             :         
     149             :         sUndefinedString = JS_InternString(context, "UNDEFINED");
     150             :         
     151             :         InitTable(context, &gOOEntityStatusConstTable);
     152             :         InitTable(context, &gOOCompassModeConstTable);
     153             :         InitTable(context, &gOOGalacticHyperspaceBehaviourConstTable);
     154             :         InitTable(context, &gOOGUIScreenIDConstTable);
     155             :         InitTable(context, &gOOScanClassConstTable);
     156             :         InitTable(context, &gOOViewIDConstTable);
     157             :         InitTable(context, &gOOShipDamageTypeConstTable);
     158             :         InitTable(context, &gOOLegalStatusReasonConstTable);
     159             :         InitTable(context, &gOOLongRangeChartModeConstTable);
     160             :         
     161             :         sInited = YES;
     162             : }
     163             : 
     164             : 
     165           0 : void OOConstToJSStringDestroy(void)
     166             : {
     167             :         NSCAssert(sInited, @"OOConstToJSStringDestroy() called while not inited.");
     168             :         sInited = NO;
     169             :         // jsString pointers are now officially junk.
     170             : }
     171             : 
     172             : 
     173           0 : static int CompareEntries(const void *a, const void *b)
     174             : {
     175             :         const TableEntry *entA = a;
     176             :         const TableEntry *entB = b;
     177             :         
     178             :         if (entA->value < entB->value)  return -1;
     179             :         if (entA->value > entB->value)  return 1;
     180             :         return 0;
     181             : }
     182             : 
     183             : 
     184           0 : static void InitTable(JSContext *context, ConstTable *table)
     185             : {
     186             :         NSCParameterAssert(context != NULL && JS_IsInRequest(context) && table != NULL);
     187             :         
     188             :         NSUInteger i;
     189             :         for(i = 0; i < table->count; i++)
     190             :         {
     191             :                 table->entries[i].jsString = JS_InternString(context, table->entries[i].cString);
     192             :         }
     193             :         
     194             :         qsort(table->entries, table->count, sizeof *table->entries, CompareEntries);
     195             : }
     196             : 
     197             : 
     198             : // MARK: Lookup
     199             : 
     200           0 : JSString *OOJSStringFromConstantPRIVATE(JSContext *context, NSInteger value, struct ConstTable *table)
     201             : {
     202             :         NSCAssert1(sInited, @"%s called before OOConstToJSStringInit().", __PRETTY_FUNCTION__);
     203             :         NSCParameterAssert(context != NULL && JS_IsInRequest(context));
     204             :         NSCParameterAssert(table != NULL && table->count > 0);
     205             :         
     206             :         // Binary search.
     207             :         NSUInteger min = 0, max = table->count - 1;
     208             :         NSInteger current;
     209             :         do
     210             :         {
     211             :                 NSUInteger mid = (min + max) / 2;
     212             :                 current = table->entries[mid].value;
     213             :                 if (current < value)
     214             :                 {
     215             :                         min = mid + 1;
     216             :                 }
     217             :                 else if (current > value)
     218             :                 {
     219             :                         max = mid - 1;
     220             :                 }
     221             :                 else
     222             :                 {
     223             :                         return table->entries[mid].jsString;
     224             :                 }
     225             :         }
     226             :         while (min <= max);
     227             :         
     228             :         return sUndefinedString;
     229             : }
     230             : 
     231             : 
     232           0 : NSUInteger OOConstantFromJSStringPRIVATE(JSContext *context, JSString *string, struct ConstTable *table, NSInteger defaultValue)
     233             : {
     234             :         NSCAssert1(sInited, @"%s called before OOConstToJSStringInit().", __PRETTY_FUNCTION__);
     235             :         NSCParameterAssert(context != NULL && JS_IsInRequest(context) && table != NULL);
     236             :         
     237             :         // Quick pass: look for pointer-equal string.
     238             :         NSUInteger i, count = table->count;
     239             :         for(i = 0; i < count; i++)
     240             :         {
     241             :                 if (table->entries[i].jsString == string)
     242             :                 {
     243             :                         return table->entries[i].value;
     244             :                 }
     245             :         }
     246             :         
     247             :         
     248             :         // Slow pass: use string comparison. This is expected to fail.
     249             :         if (string != NULL)
     250             :         {
     251             :                 for(i = 0; i < count; i++)
     252             :                 {
     253             :                         int32 result;
     254             :                         if (JS_CompareStrings(context, string, table->entries[i].jsString, &result) && result == 0)
     255             :                         {
     256             :                                 return table->entries[i].value;
     257             :                         }
     258             :                 }
     259             :         }
     260             :         
     261             :         // Fail.
     262             :         return defaultValue;
     263             : }
     264             : 
     265             : 
     266           0 : NSUInteger OOConstantFromJSValuePRIVATE(JSContext *context, jsval value, struct ConstTable *table, NSInteger defaultValue)
     267             : {
     268             :         if (EXPECT(JSVAL_IS_STRING(value)))
     269             :         {
     270             :                 return OOConstantFromJSStringPRIVATE(context, JSVAL_TO_STRING(value), table, defaultValue);
     271             :         }
     272             :         else
     273             :         {
     274             :                 return defaultValue;
     275             :         }
     276             : 
     277             : }

Generated by: LCOV version 1.14