| 1 |
/****************************************************************************** |
|---|
| 2 |
License: |
|---|
| 3 |
Copyright (c) 2008 Jarrett Billingsley |
|---|
| 4 |
|
|---|
| 5 |
This software is provided 'as-is', without any express or implied warranty. |
|---|
| 6 |
In no event will the authors be held liable for any damages arising from the |
|---|
| 7 |
use of this software. |
|---|
| 8 |
|
|---|
| 9 |
Permission is granted to anyone to use this software for any purpose, |
|---|
| 10 |
including commercial applications, and to alter it and redistribute it freely, |
|---|
| 11 |
subject to the following restrictions: |
|---|
| 12 |
|
|---|
| 13 |
1. The origin of this software must not be misrepresented; you must not |
|---|
| 14 |
claim that you wrote the original software. If you use this software in a |
|---|
| 15 |
product, an acknowledgment in the product documentation would be |
|---|
| 16 |
appreciated but is not required. |
|---|
| 17 |
|
|---|
| 18 |
2. Altered source versions must be plainly marked as such, and must not |
|---|
| 19 |
be misrepresented as being the original software. |
|---|
| 20 |
|
|---|
| 21 |
3. This notice may not be removed or altered from any source distribution. |
|---|
| 22 |
******************************************************************************/ |
|---|
| 23 |
|
|---|
| 24 |
module minid.types; |
|---|
| 25 |
|
|---|
| 26 |
version(MDRestrictedCoro) {} else |
|---|
| 27 |
import tango.core.Thread; |
|---|
| 28 |
|
|---|
| 29 |
import tango.text.convert.Layout; |
|---|
| 30 |
|
|---|
| 31 |
import minid.alloc; |
|---|
| 32 |
import minid.hash; |
|---|
| 33 |
import minid.opcodes; |
|---|
| 34 |
import minid.utils; |
|---|
| 35 |
|
|---|
| 36 |
import tango.text.convert.Format; |
|---|
| 37 |
|
|---|
| 38 |
// ================================================================================================================================================ |
|---|
| 39 |
// Public |
|---|
| 40 |
// ================================================================================================================================================ |
|---|
| 41 |
|
|---|
| 42 |
/** |
|---|
| 43 |
The native signed integer type on this platform. This is the same as ptrdiff_t but with a better name. |
|---|
| 44 |
*/ |
|---|
| 45 |
public alias ptrdiff_t word; |
|---|
| 46 |
|
|---|
| 47 |
/** |
|---|
| 48 |
The native unsigned integer type on this platform. This is the same as size_t but with a better name. |
|---|
| 49 |
*/ |
|---|
| 50 |
public alias size_t uword; |
|---|
| 51 |
|
|---|
| 52 |
/** |
|---|
| 53 |
The underlying D type used to store the MiniD 'int' type. Defaults to 'long' (64-bit signed integer). If you |
|---|
| 54 |
change it, you will end up with a functional but nonstandard implementation. |
|---|
| 55 |
*/ |
|---|
| 56 |
public alias long mdint; |
|---|
| 57 |
|
|---|
| 58 |
static assert((cast(mdint)-1) < (cast(mdint)0), "mdint must be signed"); |
|---|
| 59 |
|
|---|
| 60 |
/** |
|---|
| 61 |
The underlying D type used to store the MiniD 'float' type. Defaults to 'double'. If you change it, you will end |
|---|
| 62 |
up with a functional but nonstandard implementation. |
|---|
| 63 |
*/ |
|---|
| 64 |
public alias double mdfloat; |
|---|
| 65 |
|
|---|
| 66 |
/** |
|---|
| 67 |
The current version of MiniD. |
|---|
| 68 |
*/ |
|---|
| 69 |
public const uint MiniDVersion = MakeVersion!(2, 0); |
|---|
| 70 |
|
|---|
| 71 |
/** |
|---|
| 72 |
An alias for the type signature of a native function. It is defined as uword function(MDThread*, uword). |
|---|
| 73 |
*/ |
|---|
| 74 |
public alias uword function(MDThread*, uword) NativeFunc; |
|---|
| 75 |
|
|---|
| 76 |
/** |
|---|
| 77 |
The MiniD exception type. This is the type that is thrown whenever you throw an exception from within |
|---|
| 78 |
MiniD, or when you use the throwException API call. You can't directly instantiate this class, though, |
|---|
| 79 |
since it would be bad if you did (the interpreter needs to keep track of some internal state, which |
|---|
| 80 |
throwException does). See throwException and catchException in minid.interpreter for more info |
|---|
| 81 |
on MiniD exception handling. |
|---|
| 82 |
*/ |
|---|
| 83 |
class MDException : Exception |
|---|
| 84 |
{ |
|---|
| 85 |
package this(char[] msg) |
|---|
| 86 |
{ |
|---|
| 87 |
super(msg); |
|---|
| 88 |
} |
|---|
| 89 |
} |
|---|
| 90 |
|
|---|
| 91 |
/** |
|---|
| 92 |
This is a semi-internal exception type. Normally you won't need to know about it or catch it. This is |
|---|
| 93 |
thrown when a coroutine (thread) needs to be halted. It should never propagate out of the coroutine. |
|---|
| 94 |
The only time you might encounter it is if, in the middle of a native MiniD function, one of these |
|---|
| 95 |
is thrown, you might be able to catch it and clean up some resources, but you should rethrow it. |
|---|
| 96 |
|
|---|
| 97 |
Like the other exception types, you can't instantiate this directly, but you can halt threads with the |
|---|
| 98 |
"haltThread" function in minid.interpreter. |
|---|
| 99 |
*/ |
|---|
| 100 |
final class MDHaltException : Exception |
|---|
| 101 |
{ |
|---|
| 102 |
package this() |
|---|
| 103 |
{ |
|---|
| 104 |
super("MiniD interpreter halted"); |
|---|
| 105 |
} |
|---|
| 106 |
} |
|---|
| 107 |
|
|---|
| 108 |
/** |
|---|
| 109 |
A string constant indicating the level of coroutine support compiled in. Is one of "Restricted", |
|---|
| 110 |
"Normal", or "Extended". |
|---|
| 111 |
*/ |
|---|
| 112 |
version(MDRestrictedCoro) |
|---|
| 113 |
{ |
|---|
| 114 |
version(MDExtendedCoro) |
|---|
| 115 |
{ |
|---|
| 116 |
pragma(msg, "The 'MDRestrictedCoro' and 'MDExtendedCoro' versions are mutually exclusive."); |
|---|
| 117 |
pragma(msg, "Please define one or the other (or neither), not both.\n"); |
|---|
| 118 |
static assert(false, "FAILCOPTER."); |
|---|
| 119 |
} |
|---|
| 120 |
|
|---|
| 121 |
const char[] MDCoroSupport = "Restricted"; |
|---|
| 122 |
} |
|---|
| 123 |
else version(MDExtendedCoro) |
|---|
| 124 |
const char[] MDCoroSupport = "Extended"; |
|---|
| 125 |
else |
|---|
| 126 |
const char[] MDCoroSupport = "Normal"; |
|---|
| 127 |
|
|---|
| 128 |
// ================================================================================================================================================ |
|---|
| 129 |
// Package |
|---|
| 130 |
// ================================================================================================================================================ |
|---|
| 131 |
|
|---|
| 132 |
align(1) struct MDValue |
|---|
| 133 |
{ |
|---|
| 134 |
enum Type : uint |
|---|
| 135 |
{ |
|---|
| 136 |
// Value Types |
|---|
| 137 |
Null, // 0 |
|---|
| 138 |
Bool, |
|---|
| 139 |
Int, |
|---|
| 140 |
Float, |
|---|
| 141 |
Char, |
|---|
| 142 |
|
|---|
| 143 |
// Reference Types |
|---|
| 144 |
String, // 5 |
|---|
| 145 |
Table, |
|---|
| 146 |
Array, |
|---|
| 147 |
Function, |
|---|
| 148 |
Class, |
|---|
| 149 |
Instance, // 10 |
|---|
| 150 |
Namespace, |
|---|
| 151 |
Thread, |
|---|
| 152 |
NativeObj, |
|---|
| 153 |
WeakRef, |
|---|
| 154 |
|
|---|
| 155 |
// Internal types |
|---|
| 156 |
Upvalue, // 15 |
|---|
| 157 |
FuncDef, |
|---|
| 158 |
ArrayData |
|---|
| 159 |
} |
|---|
| 160 |
|
|---|
| 161 |
package static char[] typeString(MDValue.Type t) |
|---|
| 162 |
{ |
|---|
| 163 |
switch(t) |
|---|
| 164 |
{ |
|---|
| 165 |
case Type.Null: return "null"; |
|---|
| 166 |
case Type.Bool: return "bool"; |
|---|
| 167 |
case Type.Int: return "int"; |
|---|
| 168 |
case Type.Float: return "float"; |
|---|
| 169 |
case Type.Char: return "char"; |
|---|
| 170 |
|
|---|
| 171 |
case Type.String: return "string"; |
|---|
| 172 |
case Type.Table: return "table"; |
|---|
| 173 |
case Type.Array: return "array"; |
|---|
| 174 |
case Type.Function: return "function"; |
|---|
| 175 |
case Type.Class: return "class"; |
|---|
| 176 |
case Type.Instance: return "instance"; |
|---|
| 177 |
case Type.Namespace: return "namespace"; |
|---|
| 178 |
case Type.Thread: return "thread"; |
|---|
| 179 |
case Type.NativeObj: return "nativeobj"; |
|---|
| 180 |
case Type.WeakRef: return "weakref"; |
|---|
| 181 |
|
|---|
| 182 |
case Type.Upvalue: return "upvalue"; |
|---|
| 183 |
case Type.FuncDef: return "funcdef"; |
|---|
| 184 |
case Type.ArrayData: return "arraydata"; |
|---|
| 185 |
|
|---|
| 186 |
default: assert(false); |
|---|
| 187 |
} |
|---|
| 188 |
} |
|---|
| 189 |
|
|---|
| 190 |
package static MDValue nullValue = { type : Type.Null, mInt : 0 }; |
|---|
| 191 |
|
|---|
| 192 |
package Type type = Type.Null; |
|---|
| 193 |
|
|---|
| 194 |
union |
|---|
| 195 |
{ |
|---|
| 196 |
package bool mBool; |
|---|
| 197 |
package mdint mInt; |
|---|
| 198 |
package mdfloat mFloat; |
|---|
| 199 |
package dchar mChar; |
|---|
| 200 |
|
|---|
| 201 |
package MDBaseObject* mBaseObj; |
|---|
| 202 |
package MDString* mString; |
|---|
| 203 |
package MDTable* mTable; |
|---|
| 204 |
package MDArray* mArray; |
|---|
| 205 |
package MDFunction* mFunction; |
|---|
| 206 |
package MDClass* mClass; |
|---|
| 207 |
package MDInstance* mInstance; |
|---|
| 208 |
package MDNamespace* mNamespace; |
|---|
| 209 |
package MDThread* mThread; |
|---|
| 210 |
package MDNativeObj* mNativeObj; |
|---|
| 211 |
package MDWeakRef* mWeakRef; |
|---|
| 212 |
} |
|---|
| 213 |
|
|---|
| 214 |
package static MDValue opCall(T)(T t) |
|---|
| 215 |
{ |
|---|
| 216 |
MDValue ret = void; |
|---|
| 217 |
ret = t; |
|---|
| 218 |
return ret; |
|---|
| 219 |
} |
|---|
| 220 |
|
|---|
| 221 |
/* |
|---|
| 222 |
Returns true if this and the other value are exactly the same type and the same value. The semantics |
|---|
| 223 |
of this are exactly the same as the 'is' expression in MiniD. |
|---|
| 224 |
*/ |
|---|
| 225 |
package int opEquals(ref MDValue other) |
|---|
| 226 |
{ |
|---|
| 227 |
if(this.type != other.type) |
|---|
| 228 |
return false; |
|---|
| 229 |
|
|---|
| 230 |
switch(this.type) |
|---|
| 231 |
{ |
|---|
| 232 |
case Type.Null: return true; |
|---|
| 233 |
case Type.Bool: return this.mBool == other.mBool; |
|---|
| 234 |
case Type.Int: return this.mInt == other.mInt; |
|---|
| 235 |
case Type.Float: return this.mFloat == other.mFloat; |
|---|
| 236 |
case Type.Char: return this.mChar == other.mChar; |
|---|
| 237 |
default: return (this.mBaseObj is other.mBaseObj); |
|---|
| 238 |
} |
|---|
| 239 |
} |
|---|
| 240 |
|
|---|
| 241 |
package bool isFalse() |
|---|
| 242 |
{ |
|---|
| 243 |
return (type == Type.Null) || (type == Type.Bool && mBool == false) || |
|---|
| 244 |
(type == Type.Int && mInt == 0) || (type == Type.Float && mFloat == 0.0) || (type == Type.Char && mChar != 0); |
|---|
| 245 |
} |
|---|
| 246 |
|
|---|
| 247 |
package void opAssign(bool src) |
|---|
| 248 |
{ |
|---|
| 249 |
type = Type.Bool; |
|---|
| 250 |
mBool = src; |
|---|
| 251 |
} |
|---|
| 252 |
|
|---|
| 253 |
package void opAssign(mdint src) |
|---|
| 254 |
{ |
|---|
| 255 |
type = Type.Int; |
|---|
| 256 |
mInt = src; |
|---|
| 257 |
} |
|---|
| 258 |
|
|---|
| 259 |
package void opAssign(mdfloat src) |
|---|
| 260 |
{ |
|---|
| 261 |
type = Type.Float; |
|---|
| 262 |
mFloat = src; |
|---|
| 263 |
} |
|---|
| 264 |
|
|---|
| 265 |
package void opAssign(dchar src) |
|---|
| 266 |
{ |
|---|
| 267 |
type = Type.Char; |
|---|
| 268 |
mChar = src; |
|---|
| 269 |
} |
|---|
| 270 |
|
|---|
| 271 |
package void opAssign(MDString* src) |
|---|
| 272 |
{ |
|---|
| 273 |
type = Type.String; |
|---|
| 274 |
mString = src; |
|---|
| 275 |
} |
|---|
| 276 |
|
|---|
| 277 |
package void opAssign(MDTable* src) |
|---|
| 278 |
{ |
|---|
| 279 |
type = Type.Table; |
|---|
| 280 |
mTable = src; |
|---|
| 281 |
} |
|---|
| 282 |
|
|---|
| 283 |
package void opAssign(MDArray* src) |
|---|
| 284 |
{ |
|---|
| 285 |
type = Type.Array; |
|---|
| 286 |
mArray = src; |
|---|
| 287 |
} |
|---|
| 288 |
|
|---|
| 289 |
package void opAssign(MDFunction* src) |
|---|
| 290 |
{ |
|---|
| 291 |
type = Type.Function; |
|---|
| 292 |
mFunction = src; |
|---|
| 293 |
} |
|---|
| 294 |
|
|---|
| 295 |
package void opAssign(MDClass* src) |
|---|
| 296 |
{ |
|---|
| 297 |
type = Type.Class; |
|---|
| 298 |
mClass = src; |
|---|
| 299 |
} |
|---|
| 300 |
|
|---|
| 301 |
package void opAssign(MDInstance* src) |
|---|
| 302 |
{ |
|---|
| 303 |
type = Type.Instance; |
|---|
| 304 |
mInstance = src; |
|---|
| 305 |
} |
|---|
| 306 |
|
|---|
| 307 |
package void opAssign(MDNamespace* src) |
|---|
| 308 |
{ |
|---|
| 309 |
type = Type.Namespace; |
|---|
| 310 |
mNamespace = src; |
|---|
| 311 |
} |
|---|
| 312 |
|
|---|
| 313 |
package void opAssign(MDThread* src) |
|---|
| 314 |
{ |
|---|
| 315 |
type = Type.Thread; |
|---|
| 316 |
mThread = src; |
|---|
| 317 |
} |
|---|
| 318 |
|
|---|
| 319 |
package void opAssign(MDNativeObj* src) |
|---|
| 320 |
{ |
|---|
| 321 |
type = Type.NativeObj; |
|---|
| 322 |
mNativeObj = src; |
|---|
| 323 |
} |
|---|
| 324 |
|
|---|
| 325 |
package void opAssign(MDWeakRef* src) |
|---|
| 326 |
{ |
|---|
| 327 |
type = Type.WeakRef; |
|---|
| 328 |
mWeakRef = src; |
|---|
| 329 |
} |
|---|
| 330 |
|
|---|
| 331 |
package void opAssign(MDBaseObject* src) |
|---|
| 332 |
{ |
|---|
| 333 |
type = src.mType; |
|---|
| 334 |
mBaseObj = src; |
|---|
| 335 |
} |
|---|
| 336 |
|
|---|
| 337 |
package bool isObject() |
|---|
| 338 |
{ |
|---|
| 339 |
return type >= Type.String; |
|---|
| 340 |
} |
|---|
| 341 |
|
|---|
| 342 |
package GCObject* toGCObject() |
|---|
| 343 |
{ |
|---|
| 344 |
assert(isObject()); |
|---|
| 345 |
return cast(GCObject*)mBaseObj; |
|---|
| 346 |
} |
|---|
| 347 |
|
|---|
| 348 |
char[] toString() |
|---|
| 349 |
{ |
|---|
| 350 |
switch(type) |
|---|
| 351 |
{ |
|---|
| 352 |
case Type.Null: return "null"; |
|---|
| 353 |
case Type.Bool: return Format("{}", mBool); |
|---|
| 354 |
case Type.Int: return Format("{}", mInt); |
|---|
| 355 |
case Type.Float: return Format("{}", mFloat); |
|---|
| 356 |
case Type.Char: return Format("'{}'", mChar); |
|---|
| 357 |
case Type.String: return Format("\"{}\"", mString.toString()); |
|---|
| 358 |
case Type.Table: return Format("table {:X8}", cast(void*)mTable); |
|---|
| 359 |
case Type.Array: return Format("array {:X8}", cast(void*)mArray); |
|---|
| 360 |
case Type.Function: return Format("function {:X8}", cast(void*)mFunction); |
|---|
| 361 |
case Type.Class: return Format("class {:X8}", cast(void*)mClass); |
|---|
| 362 |
case Type.Instance: return Format("instance {:X8}", cast(void*)mInstance); |
|---|
| 363 |
case Type.Namespace: return Format("namespace {:X8}", cast(void*)mNamespace); |
|---|
| 364 |
case Type.Thread: return Format("thread {:X8}", cast(void*)mThread); |
|---|
| 365 |
case Type.NativeObj: return Format("nativeobj {:X8}", cast(void*)mNativeObj); |
|---|
| 366 |
case Type.WeakRef: return Format("weakref {:X8}", cast(void*)mWeakRef); |
|---|
| 367 |
default: assert(false); |
|---|
| 368 |
} |
|---|
| 369 |
} |
|---|
| 370 |
|
|---|
| 371 |
hash_t toHash() |
|---|
| 372 |
{ |
|---|
| 373 |
switch(type) |
|---|
| 374 |
{ |
|---|
| 375 |
case Type.Null: return 0; |
|---|
| 376 |
case Type.Bool: return typeid(typeof(mBool)).getHash(&mBool); |
|---|
| 377 |
case Type.Int: return typeid(typeof(mInt)).getHash(&mInt); |
|---|
| 378 |
case Type.Float: return typeid(typeof(mFloat)).getHash(&mFloat); |
|---|
| 379 |
case Type.Char: return typeid(typeof(mChar)).getHash(&mChar); |
|---|
| 380 |
case Type.String: return mString.hash; |
|---|
| 381 |
default: return cast(hash_t)cast(void*)mBaseObj; |
|---|
| 382 |
} |
|---|
| 383 |
} |
|---|
| 384 |
} |
|---|
| 385 |
|
|---|
| 386 |
template MDObjectMixin(uint type) |
|---|
| 387 |
{ |
|---|
| 388 |
mixin GCMixin; |
|---|
| 389 |
package MDValue.Type mType = cast(MDValue.Type)type; |
|---|
| 390 |
} |
|---|
| 391 |
|
|---|
| 392 |
struct MDBaseObject |
|---|
| 393 |
{ |
|---|
| 394 |
mixin MDObjectMixin!(MDValue.Type.Null); |
|---|
| 395 |
} |
|---|
| 396 |
|
|---|
| 397 |
struct MDString |
|---|
| 398 |
{ |
|---|
| 399 |
mixin MDObjectMixin!(MDValue.Type.String); |
|---|
| 400 |
package uword hash; |
|---|
| 401 |
package uword length; |
|---|
| 402 |
package uword cpLength; |
|---|
| 403 |
|
|---|
| 404 |
package char[] toString() |
|---|
| 405 |
{ |
|---|
| 406 |
return (cast(char*)(this + 1))[0 .. this.length]; |
|---|
| 407 |
} |
|---|
| 408 |
|
|---|
| 409 |
package uint toHash() |
|---|
| 410 |
{ |
|---|
| 411 |
return hash; |
|---|
| 412 |
} |
|---|
| 413 |
} |
|---|
| 414 |
|
|---|
| 415 |
struct MDTable |
|---|
| 416 |
{ |
|---|
| 417 |
mixin MDObjectMixin!(MDValue.Type.Table); |
|---|
| 418 |
package Hash!(MDValue, MDValue) data; |
|---|
| 419 |
} |
|---|
| 420 |
|
|---|
| 421 |
struct MDArrayData |
|---|
| 422 |
{ |
|---|
| 423 |
mixin MDObjectMixin!(MDValue.Type.ArrayData); |
|---|
| 424 |
package uword length; |
|---|
| 425 |
|
|---|
| 426 |
package MDValue[] toArray() |
|---|
| 427 |
{ |
|---|
| 428 |
return (cast(MDValue*)(this + 1))[0 .. length]; |
|---|
| 429 |
} |
|---|
| 430 |
} |
|---|
| 431 |
|
|---|
| 432 |
struct MDArray |
|---|
| 433 |
{ |
|---|
| 434 |
mixin MDObjectMixin!(MDValue.Type.Array); |
|---|
| 435 |
package MDArrayData* data; |
|---|
| 436 |
package MDValue[] slice; |
|---|
| 437 |
package bool isSlice; |
|---|
| 438 |
} |
|---|
| 439 |
|
|---|
| 440 |
struct MDFunction |
|---|
| 441 |
{ |
|---|
| 442 |
mixin MDObjectMixin!(MDValue.Type.Function); |
|---|
| 443 |
package bool isNative; |
|---|
| 444 |
package MDNamespace* environment; |
|---|
| 445 |
package MDString* name; |
|---|
| 446 |
package uword numUpvals; |
|---|
| 447 |
package MDTable* attrs; |
|---|
| 448 |
|
|---|
| 449 |
union |
|---|
| 450 |
{ |
|---|
| 451 |
package MDFuncDef* scriptFunc; |
|---|
| 452 |
package NativeFunc nativeFunc; |
|---|
| 453 |
} |
|---|
| 454 |
|
|---|
| 455 |
package MDValue[] nativeUpvals() |
|---|
| 456 |
{ |
|---|
| 457 |
return (cast(MDValue*)(this + 1))[0 .. numUpvals]; |
|---|
| 458 |
} |
|---|
| 459 |
|
|---|
| 460 |
package MDUpval*[] scriptUpvals() |
|---|
| 461 |
{ |
|---|
| 462 |
return (cast(MDUpval**)(this + 1))[0 .. numUpvals]; |
|---|
| 463 |
} |
|---|
| 464 |
|
|---|
| 465 |
static assert((MDFuncDef*).sizeof == NativeFunc.sizeof); |
|---|
| 466 |
} |
|---|
| 467 |
|
|---|
| 468 |
struct MDClass |
|---|
| 469 |
{ |
|---|
| 470 |
mixin MDObjectMixin!(MDValue.Type.Class); |
|---|
| 471 |
package MDString* name; |
|---|
| 472 |
package MDClass* parent; |
|---|
| 473 |
package MDNamespace* fields; |
|---|
| 474 |
package MDTable* attrs; |
|---|
| 475 |
package MDFunction* allocator; |
|---|
| 476 |
package MDFunction* finalizer; |
|---|
| 477 |
} |
|---|
| 478 |
|
|---|
| 479 |
struct MDInstance |
|---|
| 480 |
{ |
|---|
| 481 |
mixin MDObjectMixin!(MDValue.Type.Instance); |
|---|
| 482 |
package MDClass* parent; |
|---|
| 483 |
package MDNamespace* fields; |
|---|
| 484 |
package MDFunction* finalizer; |
|---|
| 485 |
package uword numValues; |
|---|
| 486 |
package uword extraBytes; |
|---|
| 487 |
|
|---|
| 488 |
package MDValue[] extraValues() |
|---|
| 489 |
{ |
|---|
| 490 |
return (cast(MDValue*)(this + 1))[0 .. numValues]; |
|---|
| 491 |
} |
|---|
| 492 |
|
|---|
| 493 |
package void[] extraData() |
|---|
| 494 |
{ |
|---|
| 495 |
return ((cast(void*)(this + 1)) + (numValues * MDValue.sizeof))[0 .. extraBytes]; |
|---|
| 496 |
} |
|---|
| 497 |
} |
|---|
| 498 |
|
|---|
| 499 |
struct MDNamespace |
|---|
| 500 |
{ |
|---|
| 501 |
mixin MDObjectMixin!(MDValue.Type.Namespace); |
|---|
| 502 |
package Hash!(MDString*, MDValue) data; |
|---|
| 503 |
package MDNamespace* parent; |
|---|
| 504 |
package MDString* name; |
|---|
| 505 |
package MDTable* attrs; |
|---|
| 506 |
} |
|---|
| 507 |
|
|---|
| 508 |
package alias uword AbsStack; |
|---|
| 509 |
package alias uword RelStack; |
|---|
| 510 |
|
|---|
| 511 |
struct ActRecord |
|---|
| 512 |
{ |
|---|
| 513 |
package AbsStack base; |
|---|
| 514 |
package AbsStack savedTop; |
|---|
| 515 |
package AbsStack vargBase; |
|---|
| 516 |
package AbsStack returnSlot; |
|---|
| 517 |
package MDFunction* func; |
|---|
| 518 |
package Instruction* pc; |
|---|
| 519 |
package word numReturns; |
|---|
| 520 |
package MDClass* proto; |
|---|
| 521 |
package uword numTailcalls; |
|---|
| 522 |
package uword firstResult; |
|---|
| 523 |
package uword numResults; |
|---|
| 524 |
} |
|---|
| 525 |
|
|---|
| 526 |
struct TryRecord |
|---|
| 527 |
{ |
|---|
| 528 |
package bool isCatch; |
|---|
| 529 |
package RelStack catchVarSlot; |
|---|
| 530 |
package uword actRecord; |
|---|
| 531 |
package Instruction* pc; |
|---|
| 532 |
} |
|---|
| 533 |
|
|---|
| 534 |
struct MDThread |
|---|
| 535 |
{ |
|---|
| 536 |
mixin MDObjectMixin!(MDValue.Type.Thread); |
|---|
| 537 |
|
|---|
| 538 |
public enum State |
|---|
| 539 |
{ |
|---|
| 540 |
Initial, |
|---|
| 541 |
Waiting, |
|---|
| 542 |
Running, |
|---|
| 543 |
Suspended, |
|---|
| 544 |
Dead |
|---|
| 545 |
} |
|---|
| 546 |
|
|---|
| 547 |
static char[][5] StateStrings = |
|---|
| 548 |
[ |
|---|
| 549 |
State.Initial: "initial", |
|---|
| 550 |
State.Waiting: "waiting", |
|---|
| 551 |
State.Running: "running", |
|---|
| 552 |
State.Suspended: "suspended", |
|---|
| 553 |
State.Dead: "dead" |
|---|
| 554 |
]; |
|---|
| 555 |
|
|---|
| 556 |
package TryRecord[] tryRecs; |
|---|
| 557 |
package TryRecord* currentTR; |
|---|
| 558 |
package uword trIndex = 0; |
|---|
| 559 |
|
|---|
| 560 |
package ActRecord[] actRecs; |
|---|
| 561 |
package ActRecord* currentAR; |
|---|
| 562 |
package uword arIndex = 0; |
|---|
| 563 |
|
|---|
| 564 |
package MDValue[] stack; |
|---|
| 565 |
package AbsStack stackIndex; |
|---|
| 566 |
package AbsStack stackBase; |
|---|
| 567 |
|
|---|
| 568 |
package MDValue[] results; |
|---|
| 569 |
package uword resultIndex = 0; |
|---|
| 570 |
|
|---|
| 571 |
package MDUpval* upvalHead; |
|---|
| 572 |
|
|---|
| 573 |
package MDVM* vm; |
|---|
| 574 |
package bool shouldHalt = false; |
|---|
| 575 |
|
|---|
| 576 |
package MDFunction* coroFunc; |
|---|
| 577 |
package State state = State.Initial; |
|---|
| 578 |
package uword numYields; |
|---|
| 579 |
|
|---|
| 580 |
version(MDExtendedCoro) {} else |
|---|
| 581 |
{ |
|---|
| 582 |
package uword savedCallDepth; |
|---|
| 583 |
package uword nativeCallDepth = 0; |
|---|
| 584 |
} |
|---|
| 585 |
|
|---|
| 586 |
version(MDRestrictedCoro) {} else |
|---|
| 587 |
{ |
|---|
| 588 |
// References a Fiber object |
|---|
| 589 |
package MDNativeObj* coroFiber; |
|---|
| 590 |
|
|---|
| 591 |
package Fiber getFiber() |
|---|
| 592 |
{ |
|---|
| 593 |
assert(coroFiber !is null); |
|---|
| 594 |
return cast(Fiber)cast(void*)coroFiber.obj; |
|---|
| 595 |
} |
|---|
| 596 |
} |
|---|
| 597 |
} |
|---|
| 598 |
|
|---|
| 599 |
struct MDNativeObj |
|---|
| 600 |
{ |
|---|
| 601 |
mixin MDObjectMixin!(MDValue.Type.NativeObj); |
|---|
| 602 |
package Object obj; |
|---|
| 603 |
} |
|---|
| 604 |
|
|---|
| 605 |
struct MDWeakRef |
|---|
| 606 |
{ |
|---|
| 607 |
mixin MDObjectMixin!(MDValue.Type.WeakRef); |
|---|
| 608 |
package MDBaseObject* obj; |
|---|
| 609 |
} |
|---|
| 610 |
|
|---|
| 611 |
struct Location |
|---|
| 612 |
{ |
|---|
| 613 |
enum Type |
|---|
| 614 |
{ |
|---|
| 615 |
Unknown = -2, |
|---|
| 616 |
Native = -1, |
|---|
| 617 |
Script = 0 |
|---|
| 618 |
} |
|---|
| 619 |
|
|---|
| 620 |
public MDString* file; |
|---|
| 621 |
// yes, these are 32 bits |
|---|
| 622 |
package int line = 1; |
|---|
| 623 |
package int col = 1; |
|---|
| 624 |
|
|---|
| 625 |
public static Location opCall(MDString* file, int line = 1, int col = 1) |
|---|
| 626 |
{ |
|---|
| 627 |
Location l = void; |
|---|
| 628 |
l.file = file; |
|---|
| 629 |
l.line = line; |
|---|
| 630 |
l.col = col; |
|---|
| 631 |
return l; |
|---|
| 632 |
} |
|---|
| 633 |
} |
|---|
| 634 |
|
|---|
| 635 |
struct MDUpval |
|---|
| 636 |
{ |
|---|
| 637 |
mixin MDObjectMixin!(MDValue.Type.Upvalue); |
|---|
| 638 |
|
|---|
| 639 |
package MDValue* value; |
|---|
| 640 |
package MDValue closedValue; |
|---|
| 641 |
package MDUpval* nextuv; |
|---|
| 642 |
} |
|---|
| 643 |
|
|---|
| 644 |
// The integral members of this struct are fixed at 32 bits for possible cross-platform serialization. |
|---|
| 645 |
struct MDFuncDef |
|---|
| 646 |
{ |
|---|
| 647 |
mixin MDObjectMixin!(MDValue.Type.FuncDef); |
|---|
| 648 |
|
|---|
| 649 |
package Location location; |
|---|
| 650 |
package bool isVararg; |
|---|
| 651 |
package MDString* name; |
|---|
| 652 |
package uint numParams; |
|---|
| 653 |
package ushort[] paramMasks; |
|---|
| 654 |
package uint numUpvals; |
|---|
| 655 |
package uint stackSize; |
|---|
| 656 |
package MDFuncDef*[] innerFuncs; |
|---|
| 657 |
package MDValue[] constants; |
|---|
| 658 |
package Instruction[] code; |
|---|
| 659 |
|
|---|
| 660 |
package bool isPure; |
|---|
| 661 |
package MDFunction* cachedFunc; |
|---|
| 662 |
|
|---|
| 663 |
struct SwitchTable |
|---|
| 664 |
{ |
|---|
| 665 |
package Hash!(MDValue, word) offsets; |
|---|
| 666 |
package int defaultOffset = -1; // yes, this is 32 bit, it's fixed that size |
|---|
| 667 |
} |
|---|
| 668 |
|
|---|
| 669 |
package SwitchTable[] switchTables; |
|---|
| 670 |
|
|---|
| 671 |
// Debug info. |
|---|
| 672 |
package uint[] lineInfo; |
|---|
| 673 |
package MDString*[] upvalNames; |
|---|
| 674 |
|
|---|
| 675 |
struct LocVarDesc |
|---|
| 676 |
{ |
|---|
| 677 |
package MDString* name; |
|---|
| 678 |
package uint pcStart; |
|---|
| 679 |
package uint pcEnd; |
|---|
| 680 |
package uint reg; |
|---|
| 681 |
} |
|---|
| 682 |
|
|---|
| 683 |
package LocVarDesc[] locVarDescs; |
|---|
| 684 |
} |
|---|
| 685 |
|
|---|
| 686 |
// please don't align(1) this struct, it'll mess up the D GC when it tries to look inside for pointers. |
|---|
| 687 |
struct MDVM |
|---|
| 688 |
{ |
|---|
| 689 |
package Allocator alloc; |
|---|
| 690 |
|
|---|
| 691 |
package < |
|---|