1.1 --- a/sourcepawn/vm/sp_reader.c Fri Aug 04 03:41:50 2006 +0000
1.2 +++ b/sourcepawn/vm/sp_reader.c Fri Aug 04 19:09:41 2006 +0000
1.3 @@ -79,19 +79,27 @@
1.4 }
1.5
1.6 if (!(plugin->pcode) || !(plugin->data) || !(plugin->info.stringbase))
1.7 + {
1.8 goto return_error;
1.9 + }
1.10
1.11 if ((plugin->flags == SP_FILE_DEBUG) && (!(plugin->debug.files) || !(plugin->debug.lines) || !(plugin->debug.symbols)))
1.12 + {
1.13 goto return_error;
1.14 + }
1.15
1.16 if (err)
1.17 + {
1.18 *err = SP_ERR_NONE;
1.19 + }
1.20
1.21 return plugin;
1.22
1.23 return_error:
1.24 if (err)
1.25 + {
1.26 *err = SP_ERR_FILE_FORMAT;
1.27 + }
1.28
1.29 return NULL;
1.30 }
1.31 @@ -180,7 +188,9 @@
1.32
1.33 return_error:
1.34 if (err)
1.35 + {
1.36 *err = error;
1.37 + }
1.38 return NULL;
1.39 }
1.40
1.41 @@ -200,7 +210,9 @@
1.42 if (!_ReadPlugin(&hdr, base, plugin, err))
1.43 {
1.44 if (noptr)
1.45 + {
1.46 free(plugin);
1.47 + }
1.48 return NULL;
1.49 }
1.50
2.1 --- a/sourcepawn/vm/sp_vm.c Fri Aug 04 03:41:50 2006 +0000
2.2 +++ b/sourcepawn/vm/sp_vm.c Fri Aug 04 19:09:41 2006 +0000
2.3 @@ -24,6 +24,7 @@
2.4 assert(SP_HeapRelease(&ctx, 4) == SP_ERR_INVALID_ADDRESS);
2.5 assert(SP_HeapAlloc(&ctx, 500, &l, &p) == SP_ERR_NONE);
2.6 assert(SP_HeapRelease(&ctx, l) == SP_ERR_NONE);
2.7 + assert(SP_PushCell(&ctx, 1337) == SP_ERR_NONE);
2.8
2.9 return 0;
2.10 }
2.11 @@ -109,7 +110,8 @@
2.12
2.13 int SP_FindNativeByName(sp_context_t *ctx, const char *name, uint32_t *index)
2.14 {
2.15 - uint32_t mid, low, high, diff;
2.16 + uint32_t mid, low, high;
2.17 + int diff;
2.18
2.19 high = ctx->plugin->info.natives_num - 1;
2.20 low = 0;
2.21 @@ -121,7 +123,9 @@
2.22 if (diff == 0)
2.23 {
2.24 if (index)
2.25 + {
2.26 *index = mid;
2.27 + }
2.28 return SP_ERR_NONE;
2.29 } else if (diff < 0) {
2.30 low = mid + 1;
2.31 @@ -136,10 +140,14 @@
2.32 int SP_GetNativeByIndex(sp_context_t *ctx, uint32_t index, sp_native_t **native)
2.33 {
2.34 if (index >= ctx->plugin->info.natives_num)
2.35 + {
2.36 return SP_ERR_INDEX;
2.37 + }
2.38
2.39 if (native)
2.40 + {
2.41 *native = &(ctx->natives[index]);
2.42 + }
2.43
2.44 return SP_ERR_NONE;
2.45 }
2.46 @@ -153,7 +161,8 @@
2.47
2.48 int SP_FindPublicByName(sp_context_t *ctx, const char *name, uint32_t *index)
2.49 {
2.50 - uint32_t mid, low, high, diff;
2.51 + uint32_t mid, low, high;
2.52 + int diff;
2.53
2.54 high = ctx->plugin->info.publics_num - 1;
2.55 low = 0;
2.56 @@ -165,7 +174,9 @@
2.57 if (diff == 0)
2.58 {
2.59 if (index)
2.60 + {
2.61 *index = mid;
2.62 + }
2.63 return SP_ERR_NONE;
2.64 } else if (diff < 0) {
2.65 low = mid + 1;
2.66 @@ -180,10 +191,14 @@
2.67 int SP_GetPublicByIndex(sp_context_t *ctx, uint32_t index, sp_public_t **pblic)
2.68 {
2.69 if (index >= ctx->plugin->info.publics_num)
2.70 + {
2.71 return SP_ERR_INDEX;
2.72 + }
2.73
2.74 if (pblic)
2.75 + {
2.76 *pblic = &(ctx->publics[index]);
2.77 + }
2.78
2.79 return SP_ERR_NONE;
2.80 }
2.81 @@ -198,17 +213,22 @@
2.82 int SP_GetPubvarByIndex(sp_context_t *ctx, uint32_t index, sp_pubvar_t **pubvar)
2.83 {
2.84 if (index >= ctx->plugin->info.pubvars_num)
2.85 + {
2.86 return SP_ERR_INDEX;
2.87 + }
2.88
2.89 if (pubvar)
2.90 + {
2.91 *pubvar = &(ctx->pubvars[index]);
2.92 + }
2.93
2.94 return SP_ERR_NONE;
2.95 }
2.96
2.97 int SP_FindPubvarByName(sp_context_t *ctx, const char *name, uint32_t *index)
2.98 {
2.99 - uint32_t mid, low, high, diff;
2.100 + uint32_t mid, low, high;
2.101 + int diff;
2.102
2.103 high = ctx->plugin->info.pubvars_num - 1;
2.104 low = 0;
2.105 @@ -220,7 +240,9 @@
2.106 if (diff == 0)
2.107 {
2.108 if (index)
2.109 + {
2.110 *index = mid;
2.111 + }
2.112 return SP_ERR_NONE;
2.113 } else if (diff < 0) {
2.114 low = mid + 1;
2.115 @@ -235,7 +257,9 @@
2.116 int SP_GetPubvarAddrs(sp_context_t *ctx, uint32_t index, cell_t *local_addr, cell_t **phys_addr)
2.117 {
2.118 if (index >= ctx->plugin->info.pubvars_num)
2.119 + {
2.120 return SP_ERR_INDEX;
2.121 + }
2.122
2.123 *local_addr = ctx->plugin->info.pubvars[index].address;
2.124 *phys_addr = ctx->pubvars[index].offs;
2.125 @@ -259,7 +283,9 @@
2.126 for (i=0; i<max; i++)
2.127 {
2.128 if ((ctx->natives[i].status == SP_NATIVE_OKAY) && !overwrite)
2.129 + {
2.130 continue;
2.131 + }
2.132
2.133 for (j=0; (natives[j].name) && (!num || j<num); j++)
2.134 {
2.135 @@ -276,10 +302,13 @@
2.136
2.137 int SP_BindNative(sp_context_t *ctx, sp_nativeinfo_t *native, uint32_t status)
2.138 {
2.139 - uint32_t index, err;
2.140 + uint32_t index;
2.141 + int err;
2.142
2.143 if ((err = SP_FindNativeByName(ctx, native->name, &index)) != SP_ERR_NONE)
2.144 + {
2.145 return err;
2.146 + }
2.147
2.148 ctx->natives[index].pfn = native->func;
2.149 ctx->natives[index].status = status;
2.150 @@ -308,10 +337,71 @@
2.151 int SP_LocalToPhysAddr(sp_context_t *ctx, cell_t local_addr, cell_t **phys_addr)
2.152 {
2.153 if (((local_addr >= ctx->hp) && (local_addr < ctx->sp)) || (local_addr < 0) || ((ucell_t)local_addr >= ctx->memory))
2.154 + {
2.155 return SP_ERR_INVALID_ADDRESS;
2.156 -
2.157 + }
2.158 +
2.159 if (phys_addr)
2.160 + {
2.161 *phys_addr = (cell_t *)(ctx->data + local_addr);
2.162 + }
2.163 +
2.164 + return SP_ERR_NONE;
2.165 +}
2.166 +
2.167 +int SP_PushCell(sp_context_t *ctx, cell_t value)
2.168 +{
2.169 + if ((ctx->hp + STACKMARGIN) > (cell_t)(ctx->sp - sizeof(cell_t)))
2.170 + {
2.171 + return SP_ERR_HEAPLOW;
2.172 + }
2.173 +
2.174 + ctx->sp -= sizeof(cell_t);
2.175 + *(cell_t *)(ctx->data + ctx->sp) = value;
2.176 + ctx->pushcount++;
2.177
2.178 return SP_ERR_NONE;
2.179 -}
2.180 \ No newline at end of file
2.181 +}
2.182 +
2.183 +int SP_PushCellsFromArray(sp_context_t *ctx, cell_t array[], unsigned int numcells)
2.184 +{
2.185 + unsigned int i;
2.186 + int err;
2.187 +
2.188 + for (i=0; i<numcells; i++)
2.189 + {
2.190 + if ((err = SP_PushCell(ctx, array[i])) != SP_ERR_NONE)
2.191 + {
2.192 + ctx->sp += i * sizeof(cell_t);
2.193 + ctx->pushcount -= i;
2.194 + return err;
2.195 + }
2.196 + }
2.197 +
2.198 + return SP_ERR_NONE;
2.199 +}
2.200 +
2.201 +int SP_PushCellArray(sp_context_t *ctx, cell_t *local_addr, cell_t **phys_addr, cell_t array[], unsigned int numcells)
2.202 +{
2.203 + cell_t *ph_addr;
2.204 + int err;
2.205 +
2.206 + if ((err = SP_HeapAlloc(ctx, numcells, local_addr, &ph_addr)) != SP_ERR_NONE)
2.207 + {
2.208 + return err;
2.209 + }
2.210 +
2.211 + memcpy(ph_addr, array, numcells * sizeof(cell_t));
2.212 + if (phys_addr)
2.213 + {
2.214 + *phys_addr = ph_addr;
2.215 + }
2.216 +
2.217 + if ((err = SP_PushCell(ctx, *local_addr)) != SP_ERR_NONE)
2.218 + {
2.219 + SP_HeapRelease(ctx, *local_addr);
2.220 + return err;
2.221 + }
2.222 +
2.223 + return SP_ERR_NONE;
2.224 +}
3.1 --- a/sourcepawn/vm/sp_vm.h Fri Aug 04 03:41:50 2006 +0000
3.2 +++ b/sourcepawn/vm/sp_vm.h Fri Aug 04 19:09:41 2006 +0000
3.3 @@ -8,6 +8,7 @@
3.4 ** Note that all functions return a non-zero error code on failure
3.5 * unless otherwise noted.
3.6 * All input pointers must be valid unless otherwise noted as optional.
3.7 + * All output pointers on failure are undefined.
3.8 * All local address are guaranteed to be positive. However, they are stored
3.9 * as signed integers, because they must logically fit inside a cell.
3.10 */
3.11 @@ -195,6 +196,7 @@
3.12
3.13 /**
3.14 * Pushes an array of cells onto the stack. Increases the parameter count by one.
3.15 + * If the function returns an error it will fail entirely, releasing anything allocated in the process.
3.16 * Note that this does not release the heap, so you should release it after
3.17 * calling SP_Execute().
3.18 *
3.19 @@ -229,6 +231,7 @@
3.20 /**
3.21 * Individually pushes each cell of an array of cells onto the stack. Increases the
3.22 * parameter count by the number of cells pushed.
3.23 + * If the function returns an error it will fail entirely, releasing anything allocated in the process.
3.24 *
3.25 * @param ctx Context pointer.
3.26 * @param array Array of cells to read from.
3.27 @@ -260,7 +263,7 @@
3.28 int SP_BindNative(sp_context_t *ctx, sp_nativeinfo_t *native, uint32_t status);
3.29
3.30 /**
3.31 - * Binds a single native to any non-registered native.
3.32 + * Binds a single native to any non-registered or pending native.
3.33 * Status is automatically set to pending.
3.34 *
3.35 * @param ctx Context pointer.