this repo has no description
1/* Copyright (c) Facebook, Inc. and its affiliates. (http://www.facebook.com) */
2#pragma once
3
4#include "bytecode.h"
5#include "capi.h"
6#include "handles.h"
7#include "heap.h"
8#include "interpreter-gen.h"
9#include "interpreter.h"
10#include "layout.h"
11#include "modules.h"
12#include "mutex.h"
13#include "symbols.h"
14#include "view.h"
15
16namespace py {
17
18class AttributeInfo;
19class Heap;
20class RawObject;
21class RawTuple;
22class PointerVisitor;
23class Thread;
24
25enum LayoutTypeTransition {
26 kFrom = 0,
27 kTo = 1,
28 kResult = 2,
29 kTransitionSize,
30};
31
32using AtExitFn = void (*)(void*);
33
34using DictEq = RawObject (*)(Thread*, RawObject, RawObject);
35
36enum class ReadOnly : bool {
37 ReadWrite,
38 ReadOnly,
39};
40
41struct RandomState {
42 uint64_t state[2];
43 uint64_t siphash24_secret;
44 uint64_t extra_secret[3];
45};
46RandomState randomState();
47RandomState randomStateFromSeed(uint64_t seed);
48
49enum class StdioState {
50 kBuffered,
51 kUnbuffered,
52};
53
54class Runtime {
55 public:
56 Runtime(word heap_size, Interpreter* interpreter, RandomState random_seed,
57 StdioState stdio_state);
58 ~Runtime();
59
60 // Completes the runtime initialization. Should be called after
61 // `initializeSys`.
62 RawObject initialize(Thread* thread);
63
64 bool initialized() { return initialized_; }
65
66 // TODO(T75349221): Make createXXX functions private or remove them
67 RawObject createLargeInt(word num_digits);
68 RawObject createLargeStr(word length);
69
70 // Allocate memory for JITed code.
71 bool allocateForMachineCode(word size, uword* address_out);
72
73 RawObject newBoundMethod(const Object& function, const Object& self);
74
75 RawObject newBytearray();
76 RawObject newBytearrayIterator(Thread* thread, const Bytearray& bytearray);
77
78 RawObject newBytes(word length, byte fill);
79 RawObject newBytesWithAll(View<byte> array);
80 RawObject newBytesIterator(Thread* thread, const Bytes& bytes);
81
82 RawObject newTraceback();
83
84 RawObject newType();
85
86 RawObject newTypeWithMetaclass(LayoutId metaclass_id);
87
88 RawObject newTypeProxy(const Type& type);
89
90 RawObject newCell();
91
92 RawObject newClassMethod();
93
94 // TODO(T55871582): Remove code paths that can raise from the Runtime
95 RawObject newCode(word argcount, word posonlyargcount, word kwonlyargcount,
96 word nlocals, word stacksize, word flags,
97 const Object& code, const Object& consts,
98 const Object& names, const Object& varnames,
99 const Object& freevars, const Object& cellvars,
100 const Object& filename, const Object& name,
101 word firstlineno, const Object& lnotab);
102
103 RawObject newBuiltinCode(word argcount, word posonlyargcount,
104 word kwonlyargcount, word flags,
105 BuiltinFunction function,
106 const Object& parameter_names,
107 const Object& name_str);
108
109 RawObject newComplex(double real, double imag);
110
111 RawObject newCoroutine();
112
113 RawObject newDeque();
114
115 RawObject newDequeIterator(const Deque& deque, word index);
116 RawObject newDequeReverseIterator(const Deque& deque, word index);
117
118 RawObject newDict();
119 RawObject newDictWithSize(word initial_size);
120
121 RawObject newDictItemIterator(Thread* thread, const Dict& dict);
122 RawObject newDictItems(Thread* thread, const Dict& dict);
123 RawObject newDictKeyIterator(Thread* thread, const Dict& dict);
124 RawObject newDictKeys(Thread* thread, const Dict& dict);
125 RawObject newDictValueIterator(Thread* thread, const Dict& dict);
126 RawObject newDictValues(Thread* thread, const Dict& dict);
127
128 RawObject newFloat(double value);
129
130 RawObject newSet();
131
132 RawObject emptyFrozenSet();
133 RawObject newFrozenSet();
134
135 RawObject newFunction(Thread* thread, const Object& name, const Object& code,
136 word flags, word argcount, word total_args,
137 word total_vars, const Object& stacksize_or_builtin,
138 Function::Entry entry, Function::Entry entry_kw,
139 Function::Entry entry_ex);
140
141 RawObject newFunctionWithCode(Thread* thread, const Object& qualname,
142 const Code& code, const Object& module_obj);
143
144 RawObject newExceptionState();
145
146 RawObject newFrameProxy(Thread* thread, const Object& function,
147 const Object& lasti);
148
149 RawObject newGenerator();
150
151 RawObject newGeneratorFrame(const Function& function);
152
153 RawObject newInstance(const Layout& layout);
154 RawObject newInstanceWithSize(LayoutId layout_id, word object_size);
155
156 // Create a new Int from a signed value.
157 RawObject newInt(word value);
158
159 // Create a new Int from an unsigned value.
160 RawObject newIntFromUnsigned(uword value);
161
162 RawObject newLargeIntFromWord(word value);
163
164 // Create a new LargeInt from a sequence of digits, which will be interpreted
165 // as a signed, two's-complement number. The digits must satisfy the
166 // invariants listed on the LargeInt class.
167 RawObject newLargeIntWithDigits(View<uword> digits);
168
169 RawObject newLayout(LayoutId id);
170
171 RawObject newList();
172
173 RawObject newListIterator(const Object& list);
174
175 RawObject newSeqIterator(const Object& sequence);
176
177 RawObject newSlotDescriptor(const Type& type, const Object& name);
178
179 // Create a new MemoryView object. Initializes the view format to "B".
180 RawObject newMemoryView(Thread* thread, const Object& obj,
181 const Object& buffer, word length,
182 ReadOnly read_only);
183 // Create a new MemoryView object from a C pointer. Initializes the view
184 // format to "B".
185 RawObject newMemoryViewFromCPtr(Thread* thread, const Object& obj, void* ptr,
186 word length, ReadOnly read_only);
187
188 // Create a new Mmap object.
189 RawObject newMmap();
190
191 RawObject newModule(const Object& name);
192
193 RawObject newModuleProxy(const Module& module);
194
195 RawObject newMutableBytesUninitialized(word size);
196
197 RawObject newMutableBytesZeroed(word size);
198
199 // Returns an Int that stores the numerical address of the pointer.
200 RawObject newIntFromCPtr(void* ptr);
201
202 // Returns the singleton empty mutablebytes. Guaranteed to not allocate.
203 RawObject emptyMutableBytes();
204
205 // Returns the singleton empty slice. Guaranteed to not allocate.
206 RawObject emptySlice();
207
208 // Returns the singleton empty tuple. Guaranteed to not allocate.
209 RawObject emptyTuple();
210
211 // Return a new, zero-initialized, mutable tuple of the given length.
212 RawObject newMutableTuple(word length);
213
214 // Return a new tuple containing the specified arguments.
215 RawObject newTupleWith1(const Object& item1);
216 RawObject newTupleWith2(const Object& item1, const Object& item2);
217 RawObject newTupleWith3(const Object& item1, const Object& item2,
218 const Object& item3);
219 RawObject newTupleWith4(const Object& item1, const Object& item2,
220 const Object& item3, const Object& item4);
221 RawObject newTupleWithN(word num_items, const Object* item1, ...);
222
223 RawObject newPointer(void* cptr, word length);
224
225 RawObject newProperty(const Object& getter, const Object& setter,
226 const Object& deleter);
227
228 RawObject newRange(const Object& start, const Object& stop,
229 const Object& step);
230
231 RawObject newLongRangeIterator(const Int& start, const Int& stop,
232 const Int& step);
233
234 RawObject newRangeIterator(word start, word step, word length);
235
236 RawObject newSetIterator(const Object& set);
237
238 RawObject newSlice(const Object& start, const Object& stop,
239 const Object& step);
240
241 RawObject newStaticMethod();
242
243 RawObject newStrArray();
244
245 RawObject newStrFromCStr(const char* c_str);
246 RawObject strFromStrArray(const StrArray& array);
247
248 // Creates a new string constructed from a format and a list of arguments,
249 // similar to sprintf.
250 // %c formats an ASCII character
251 // %w formats a word
252 // %C formats a unicode code point
253 // %S formats a Str object
254 // %T gets the type name of an object and formats that
255 // %Y formats a SymbolId
256 RawObject newStrFromFmt(const char* fmt, ...);
257 RawObject newStrFromFmtV(Thread* thread, const char* fmt, va_list args);
258 RawObject newStrFromUTF32(View<int32_t> code_units);
259 RawObject newStrWithAll(View<byte> code_units);
260
261 RawObject newStrIterator(const Object& str);
262
263 RawObject newSuper();
264
265 RawObject newTupleIterator(const Tuple& tuple, word length);
266
267 // Constructors from _contextvars
268 RawObject newContext(const Dict& data);
269 RawObject newContextVar(const Str& name, const Object& default_value);
270 RawObject newToken(const Context& ctx, const ContextVar& ctx_var,
271 const Object& old_value);
272
273 void processCallbacks();
274 void processFinalizers();
275
276 RawObject strConcat(Thread* thread, const Str& left, const Str& right);
277 RawObject strJoin(Thread* thread, const Str& sep, const Tuple& items,
278 word allocated);
279
280 // Creates a new Str containing `str` repeated `count` times.
281 RawObject strRepeat(Thread* thread, const Str& str, word count);
282
283 RawObject strSlice(Thread* thread, const Str& str, word start, word stop,
284 word step);
285
286 RawObject newValueCell();
287
288 RawObject newWeakLink(Thread* thread, const Object& referent,
289 const Object& prev, const Object& next);
290
291 RawObject newWeakRef(Thread* thread, const Object& referent);
292
293 RawObject ellipsis() { return ellipsis_; }
294
295 word builtinsModuleId() { return builtins_module_id_; }
296 void setBuiltinsModuleId(word builtins_module_id) {
297 builtins_module_id_ = builtins_module_id;
298 }
299
300 RawObject moduleDunderGetattribute() { return module_dunder_getattribute_; }
301 RawObject objectDunderClass() { return object_dunder_class_; }
302 RawObject objectDunderEq() { return object_dunder_eq_; }
303 RawObject objectDunderGetattribute() { return object_dunder_getattribute_; }
304 RawObject objectDunderHash() { return object_dunder_hash_; }
305 RawObject objectDunderInit() { return object_dunder_init_; }
306 RawObject objectDunderNew() { return object_dunder_new_; }
307 RawObject objectDunderSetattr() { return object_dunder_setattr_; }
308 RawObject strDunderEq() { return str_dunder_eq_; }
309 RawObject strDunderHash() { return str_dunder_hash_; }
310 RawValueCell sysStderr() { return ValueCell::cast(sys_stderr_); }
311 RawValueCell sysStdin() { return ValueCell::cast(sys_stdin_); }
312 RawValueCell sysStdout() { return ValueCell::cast(sys_stdout_); }
313 RawObject typeDunderGetattribute() { return type_dunder_getattribute_; }
314
315 RawObject profilingNewThread() { return profiling_new_thread_; }
316 RawObject profilingCall() { return profiling_call_; }
317 RawObject profilingReturn() { return profiling_return_; }
318
319 void setProfiling(const Object& new_thread_func, const Object& call_func,
320 const Object& return_func);
321
322 void reinitInterpreter();
323
324 void builtinTypeCreated(Thread* thread, const Type& type);
325
326 void cacheBuildClass(Thread* thread, const Module& builtins);
327 void cacheSysInstances(Thread* thread, const Module& sys);
328
329 static RawObject internStr(Thread* thread, const Object& str);
330 static RawObject internStrFromAll(Thread* thread, View<byte> bytes);
331 static RawObject internStrFromCStr(Thread* thread, const char* c_str);
332 static RawObject internLargeStr(Thread* thread, const Object& str);
333 // This function should only be used for `CHECK()`/`DCHECK()`. It is as slow
334 // as the whole `internStr()` operation and will always return true for small
335 // strings, even when the user did not explicitly intern them.
336 static bool isInternedStr(Thread* thread, const Object& str);
337
338 enum class CompactionDestination { kImmortalPartition, kNewPartition };
339 void collectGarbage() {
340 collectGarbageInto(CompactionDestination::kNewPartition);
341 }
342 void immortalizeCurrentHeapObjects() {
343 collectGarbageInto(CompactionDestination::kImmortalPartition);
344 }
345 void collectGarbageInto(CompactionDestination destination);
346
347 // Creates a new thread and adds it to the runtime.
348 Thread* newThread();
349
350 // Removes the specified thread from the runtime and deletes it.
351 void deleteThread(Thread* thread);
352
353 // Compute hash value suitable for `RawObject::operator==` (aka `a is b`)
354 // equality tests.
355 word hash(RawObject object);
356 // Compute hash value for objects with byte payload. This is a helper to
357 // implement `xxxHash()` functions.
358 word valueHash(RawObject object);
359
360 word identityHash(RawObject object);
361
362 word bytesHash(View<byte> array);
363
364 uword random();
365
366 Heap* heap() { return &heap_; }
367
368 Interpreter* interpreter() { return interpreter_.get(); }
369
370 RawObject* finalizableReferences();
371
372 void visitRootsWithoutApiHandles(PointerVisitor* visitor);
373
374 RawObject findModule(const Object& name);
375 RawObject findModuleById(SymbolId name);
376 RawObject lookupNameInModule(Thread* thread, SymbolId module_name,
377 SymbolId name);
378
379 // Write the traceback to the given file object. If success, return None.
380 // Else, return Error.
381 RawObject printTraceback(Thread* thread, word fd);
382
383 // Returns the implicit bases -- (object,) -- for a new class.
384 RawObject implicitBases();
385
386 // Gets the internal notion of type, rather than the user-visible type.
387 RawObject concreteTypeAt(LayoutId layout_id);
388 inline RawObject concreteTypeOf(RawObject object) {
389 return concreteTypeAt(object.layoutId());
390 }
391
392 // Sets the internal type for layouts with a different describedType.
393 void setLargeBytesType(const Type& type);
394 void setLargeIntType(const Type& type);
395 void setLargeStrType(const Type& type);
396 void setSmallBytesType(const Type& type);
397 void setSmallIntType(const Type& type);
398 void setSmallStrType(const Type& type);
399
400 RawType typeOf(RawObject object) {
401 return Layout::cast(layoutOf(object)).describedType().rawCast<RawType>();
402 }
403
404 RawObject typeAt(LayoutId layout_id);
405 RawObject layoutAt(LayoutId layout_id) {
406 DCHECK(layout_id != LayoutId::kError, "Error has no Layout");
407 return Tuple::cast(layouts_).at(static_cast<word>(layout_id));
408 }
409 void layoutAtPut(LayoutId layout_id, RawObject object);
410 // Get layout for `layout_id` and attempt not to crash for invalid ids. This
411 // is for debug dumpers. Do not use for other purposes!
412 RawObject layoutAtSafe(LayoutId layout_id);
413 RawObject layoutOf(RawObject obj) {
414 if (obj.isHeapObject()) {
415 return layoutAt(RawHeapObject::cast(obj).header().layoutId());
416 }
417 return layoutAt(
418 static_cast<LayoutId>(obj.raw() & Object::kImmediateTagMask));
419 }
420
421 // Raw access to the MutableTuple of Layouts. Intended only for use by the GC.
422 RawObject layouts() { return layouts_; }
423 void setLayouts(RawObject layouts) { layouts_ = layouts; }
424
425 // Raw access to the Tuple of layout transitions while setting __class__.
426 // Intended only for use by the GC.
427 RawObject layoutTypeTransitions() { return layout_type_transitions_; }
428 void setLayoutTypeTransitions(RawObject value) {
429 layout_type_transitions_ = value;
430 }
431
432 void layoutSetTupleOverflow(RawLayout layout);
433
434 LayoutId reserveLayoutId(Thread* thread);
435
436 word reserveModuleId();
437
438 RawObject buildClass() { return build_class_; }
439
440 RawObject displayHook() { return display_hook_; }
441
442 // Returns modules mapping (aka `sys.modules`).
443 RawObject modules() { return modules_; }
444
445 char* capiStateData() { return capi_state_; }
446
447 void setAtExit(AtExitFn func, void* ctx) {
448 DCHECK(at_exit_ == nullptr,
449 "setAtExit should not override existing at_exit function");
450 at_exit_ = func;
451 at_exit_context_ = ctx;
452 }
453
454 void callAtExit() {
455 if (at_exit_ == nullptr) return;
456 at_exit_(at_exit_context_);
457 at_exit_ = nullptr;
458 at_exit_context_ = nullptr;
459 }
460
461 Symbols* symbols() { return symbols_; }
462
463 // Provides a growth strategy for mutable sequences. Grows by a factor of 1.5,
464 // scaling up to the requested capacity if the initial factor is insufficient.
465 // Always grows the sequence.
466 static word newCapacity(word curr_capacity, word min_capacity);
467
468 // Ensures that the byte array has at least the desired capacity.
469 // Allocates if the existing capacity is insufficient.
470 void bytearrayEnsureCapacity(Thread* thread, const Bytearray& array,
471 word min_capacity);
472
473 // Appends multiple bytes to the end of the array.
474 void bytearrayExtend(Thread* thread, const Bytearray& array, View<byte> view);
475 void bytearrayIadd(Thread* thread, const Bytearray& array, const Bytes& bytes,
476 word length);
477
478 // Returns a new Bytes containing the elements of `left` and `right`.
479 RawObject bytesConcat(Thread* thread, const Bytes& left, const Bytes& right);
480
481 // Returns a copy of a bytes object
482 RawObject bytesCopy(Thread* thread, const Bytes& src);
483
484 // Makes a new copy of the `original` bytes with the specified `size`.
485 // If the new length is less than the old length, truncate the bytes to fit.
486 // If the new length is greater than the old length, pad with trailing zeros.
487 RawObject bytesCopyWithSize(Thread* thread, const Bytes& original,
488 word new_length);
489
490 // Checks whether the specified range of `bytes` ends with the given `suffix`.
491 // Returns `Bool::trueObj()` if the suffix matches, else `Bool::falseObj()`.
492 RawObject bytesEndsWith(const Bytes& bytes, word bytes_len,
493 const Bytes& suffix, word suffix_len, word start,
494 word end);
495
496 // Returns a new Bytes from the first `length` int-like elements in the tuple.
497 RawObject bytesFromTuple(Thread* thread, const Tuple& items, word length);
498
499 // Creates a new Bytes or MutableBytes (depending on `source`'s type)
500 // containing the first `length` bytes of the `source` repeated `count` times.
501 // Specifies `length` explicitly to allow for Bytearrays with extra allocated
502 // space.
503 RawObject bytesRepeat(Thread* thread, const Bytes& source, word length,
504 word count);
505
506 // Replace the occurances of old_bytes with new_bytes in src up to max_count.
507 // If no instances of old_bytes exist, old_bytes == new_bytes, or max_count is
508 // zero, return src unmodified.
509 // NOTE: a negative max_count value is used to signify that all instaces of
510 // old_bytes should be replaced
511 RawObject bytesReplace(Thread* thread, const Bytes& src,
512 const Bytes& old_bytes, word old_len,
513 const Bytes& new_bytes, word new_len, word max_count);
514
515 // Returns a new Bytes that contains the specified slice of bytes.
516 RawObject bytesSlice(Thread* thread, const Bytes& bytes, word start,
517 word stop, word step);
518
519 // Checks whether the specified range of bytes starts with the given prefix.
520 // Returns Bool::trueObj() if the suffix matches, else Bool::falseObj().
521 RawObject bytesStartsWith(const Bytes& bytes, word bytes_len,
522 const Bytes& prefix, word prefix_len, word start,
523 word end);
524
525 // Returns a new Bytes or MutableBytes copy of `bytes` with all of
526 // the bytes in `del` removed, where the remaining bytes are mapped using
527 // `table`.
528 RawObject bytesTranslate(Thread* thread, const Bytes& bytes, word length,
529 const Bytes& table, word table_len, const Bytes& del,
530 word del_len);
531
532 // Returns the repr-string for a byteslike object. The caller must provide the
533 // size of the resulting string, accounting for escaping, and the correct
534 // delimiter character, which is either a single- or double-quote.
535 RawObject byteslikeRepr(Thread* thread, const Byteslike& byteslike,
536 word result_length, byte delimiter);
537
538 // Ensures that the list has at least the desired capacity.
539 // Allocates if the existing capacity is insufficient.
540 void listEnsureCapacity(Thread* thread, const List& list, word min_capacity);
541
542 // Appends an element to the end of the list.
543 void listAdd(Thread* thread, const List& list, const Object& value);
544
545 // Create a MutableBytes object from a given Bytes
546 RawObject mutableBytesFromBytes(Thread* thread, const Bytes& bytes);
547 RawObject mutableBytesWith(word length, byte value);
548
549 RawObject tupleSubseq(Thread* thread, const Tuple& tuple, word start,
550 word length);
551
552 // Creates a layout that is a subclass of a built-in class and zero or more
553 // additional built-in attributes.
554 RawObject layoutCreateSubclassWithBuiltins(Thread* thread,
555 LayoutId subclass_id,
556 LayoutId superclass_id,
557 View<BuiltinAttribute> attributes,
558 word size);
559
560 RawObject layoutNewAttribute(const Object& name, AttributeInfo info);
561
562 // Performs a simple scan of the bytecode and collects all attributes that
563 // are set via `self.<attribute> =` into attributes.
564 void collectAttributes(const Code& code, const Dict& attributes);
565
566 // Returns type's __init__ method, or None
567 RawObject classConstructor(const Type& type);
568
569 // Implements `receiver.name`
570 NODISCARD RawObject attributeAt(Thread* thread, const Object& receiver,
571 const Object& name);
572 NODISCARD RawObject attributeAtSetLocation(Thread* thread,
573 const Object& receiver,
574 const Object& name,
575 LoadAttrKind* kind,
576 Object* location_out);
577 NODISCARD RawObject attributeAtById(Thread* thread, const Object& receiver,
578 SymbolId id);
579 NODISCARD RawObject attributeAtByCStr(Thread* thread, const Object& receiver,
580 const char* name);
581
582 // Implements `del receiver.name`
583 NODISCARD RawObject attributeDel(Thread* thread, const Object& receiver,
584 const Object& name);
585
586 // Looks up the named attribute in the layout.
587 //
588 // If the attribute is found this returns true and sets info.
589 // Returns false otherwise.
590 static bool layoutFindAttribute(RawLayout layout, const Object& name,
591 AttributeInfo* info);
592
593 // Creates a copy of a layout with a new layout id.
594 //
595 // The new layout shares the in-object and overflow attributes and contains
596 // no outgoing edges.
597 RawObject layoutCreateCopy(Thread* thread, const Layout& layout);
598
599 // Add the attribute to the overflow array.
600 //
601 // This returns a new layout by either following a pre-existing edge or
602 // adding one.
603 RawObject layoutAddAttribute(Thread* thread, const Layout& layout,
604 const Object& name, word flags,
605 AttributeInfo* info);
606
607 // Create a new tuple for the name, info pair and return a new tuple
608 // containing entries + entry.
609 RawObject layoutAddAttributeEntry(Thread* thread, const Tuple& entries,
610 const Object& name, AttributeInfo info);
611
612 // Change the described type of a layout. Follow an edge if it exists, or
613 // create a new layout otherwise.
614 // This is used when assigning to __class__ on an instance.
615 RawObject layoutSetDescribedType(Thread* thread, const Layout& from,
616 const Type& to);
617
618 // Delete the named attribute from the layout.
619 //
620 // If the attribute exists, this returns a new layout by either following
621 // a pre-existing edge or adding one.
622 //
623 // If the attribute doesn't exist, Error::object() is returned.
624 RawObject layoutDeleteAttribute(Thread* thread, const Layout& layout,
625 const Object& name, AttributeInfo info);
626
627 // Return the dict overflow-only layout derived from `type`, for instances
628 // having `num_in_object_attr` in-object attributes.
629 RawObject typeDictOnlyLayout(Thread* thread, const Type& type,
630 word num_in_object_attr);
631
632 // For commonly-subclassed builtin types, define isInstanceOfFoo(RawObject)
633 // that does a check including subclasses (unlike RawObject::isFoo(), which
634 // only gets exact types).
635#define DEFINE_IS_INSTANCE(ty) \
636 bool isInstanceOf##ty(RawObject obj) { \
637 if (obj.is##ty()) return true; \
638 return typeOf(obj).rawCast<RawType>().builtinBase() == LayoutId::k##ty; \
639 }
640 DEFINE_IS_INSTANCE(Array)
641 DEFINE_IS_INSTANCE(BufferedRandom)
642 DEFINE_IS_INSTANCE(BufferedReader)
643 DEFINE_IS_INSTANCE(BufferedWriter)
644 DEFINE_IS_INSTANCE(Bytearray)
645 DEFINE_IS_INSTANCE(Bytes)
646 DEFINE_IS_INSTANCE(BytesIO)
647 DEFINE_IS_INSTANCE(ClassMethod)
648 DEFINE_IS_INSTANCE(Complex)
649 DEFINE_IS_INSTANCE(Deque)
650 DEFINE_IS_INSTANCE(Dict)
651 DEFINE_IS_INSTANCE(FileIO)
652 DEFINE_IS_INSTANCE(Float)
653 DEFINE_IS_INSTANCE(FrozenSet)
654 DEFINE_IS_INSTANCE(ImportError)
655 DEFINE_IS_INSTANCE(Int)
656 DEFINE_IS_INSTANCE(List)
657 DEFINE_IS_INSTANCE(Mmap)
658 DEFINE_IS_INSTANCE(Module)
659 DEFINE_IS_INSTANCE(Property)
660 DEFINE_IS_INSTANCE(Set)
661 DEFINE_IS_INSTANCE(StaticMethod)
662 DEFINE_IS_INSTANCE(StopIteration)
663 DEFINE_IS_INSTANCE(Str)
664 DEFINE_IS_INSTANCE(StringIO)
665 DEFINE_IS_INSTANCE(SystemExit)
666 DEFINE_IS_INSTANCE(TextIOWrapper)
667 DEFINE_IS_INSTANCE(Tuple)
668 DEFINE_IS_INSTANCE(Type)
669 DEFINE_IS_INSTANCE(UnicodeDecodeError)
670 DEFINE_IS_INSTANCE(UnicodeEncodeError)
671 DEFINE_IS_INSTANCE(UnicodeError)
672 DEFINE_IS_INSTANCE(UnicodeTranslateError)
673 DEFINE_IS_INSTANCE(WeakRef)
674#undef DEFINE_IS_INSTANCE
675
676 // User-defined subclasses of immediate types have no corresponding LayoutId,
677 // so we detect them by looking for an object that is a subclass of a
678 // particular immediate type but not exactly that type.
679#define DEFINE_IS_USER_INSTANCE(ty) \
680 bool isInstanceOfUser##ty##Base(RawObject obj) { \
681 return !obj.is##ty() && \
682 typeOf(obj).rawCast<RawType>().builtinBase() == LayoutId::k##ty; \
683 }
684 DEFINE_IS_USER_INSTANCE(Bytes)
685 DEFINE_IS_USER_INSTANCE(Complex)
686 DEFINE_IS_USER_INSTANCE(Float)
687 DEFINE_IS_USER_INSTANCE(Int)
688 DEFINE_IS_USER_INSTANCE(Str)
689 DEFINE_IS_USER_INSTANCE(Tuple)
690 DEFINE_IS_USER_INSTANCE(WeakRef)
691#undef DEFINE_IS_USER_INSTANCE
692
693 bool isInstanceOfNativeProxy(RawObject obj) {
694 // Note that this reports true when the object can be used safely via
695 // `RawNativeProxy` or assigned to a `NativeProxy` handle. The function
696 // name is required for `Hanlde<>` to work. It is misleading in that we
697 // consider native proxy to be more of a property of the type than is
698 // orthogonal to the subtyping relationships.
699 return typeOf(obj).rawCast<RawType>().hasNativeData();
700 }
701
702 // BaseException must be handled specially because it has builtin subclasses
703 // that are visible to managed code.
704 bool isInstanceOfBaseException(RawObject obj) {
705 return typeOf(obj).rawCast<RawType>().isBaseExceptionSubclass();
706 }
707
708 // SetBase must also be handled specially because many builtin functions
709 // accept set or frozenset, despite them not having a common ancestor.
710 bool isInstanceOfSetBase(RawObject instance) {
711 if (instance.isSetBase()) {
712 return true;
713 }
714 LayoutId builtin_base = typeOf(instance).rawCast<RawType>().builtinBase();
715 return builtin_base == LayoutId::kSet ||
716 builtin_base == LayoutId::kFrozenSet;
717 }
718
719 bool isInstanceOfUnicodeErrorBase(RawObject instance) {
720 return isInstanceOfUnicodeDecodeError(instance) ||
721 isInstanceOfUnicodeEncodeError(instance) ||
722 isInstanceOfUnicodeTranslateError(instance);
723 }
724
725 inline bool isByteslike(RawObject obj) {
726 return isInstanceOfBytes(obj) || isInstanceOfBytearray(obj) ||
727 obj.isMemoryView() || obj.isArray();
728 }
729
730 // Clear the allocated memory from all extension related objects
731 void deallocExtensions();
732
733 // Initial data of the set.
734 static const int kSetGrowthFactor = 2;
735 static const int kInitialSetCapacity = 8;
736
737 static const word kInitialInternSetCapacity = 8192;
738
739 static const word kInitialLayoutTupleCapacity = 1024;
740
741 void setRandomState(RandomState random_state) {
742 random_state_ = random_state;
743 }
744
745 // Returns whether object's class provides a __call__ method
746 //
747 // If its type defines a __call__, it is also callable (even if __call__ is
748 // not actually callable).
749 // Note that this does not include __call__ defined on the particular
750 // instance, only __call__ defined on the type.
751 bool isCallable(Thread* thread, const Object& obj);
752
753 // Returns whether object's class provides a __delete__ method
754 bool isDeleteDescriptor(Thread* thread, const Object& object);
755
756 // Returns whether object's class provides a __next__ method
757 bool isIterator(Thread* thread, const Object& obj);
758
759 // Return whether object's class supports the sequence protocol
760 bool isSequence(Thread* thread, const Object& obj);
761
762 // Return whether object's class provides a __getitem__ method
763 bool isMapping(Thread* thread, const Object& obj);
764
765 // Converts bytes object into an int object. The conversion is performed
766 // with the specified endianness. `is_signed` specifies whether the highest
767 // bit is considered a sign.
768 RawObject bytesToInt(Thread* thread, const Bytes& bytes, endian endianness,
769 bool is_signed);
770
771 static uint64_t hashWithKey(const Bytes& bytes, uint64_t key);
772
773 // Returns the sum of `left` and `right`.
774 RawObject intAdd(Thread* thread, const Int& left, const Int& right);
775
776 // Returns the result of bitwise AND of the arguments
777 RawObject intBinaryAnd(Thread* thread, const Int& left, const Int& right);
778
779 // Returns the result of bitwise left shift of the arguments
780 RawObject intBinaryLshift(Thread* thread, const Int& num, const Int& amount);
781
782 // Returns the result of bitwise logical OR of the arguments
783 RawObject intBinaryOr(Thread* thread, const Int& left, const Int& right);
784
785 // Returns the result of bitwise right shift of `num` by `shift`.
786 RawObject intBinaryRshift(Thread* thread, const Int& num, const Int& amount);
787
788 // Returns the result of bitwise XOR of the arguments
789 RawObject intBinaryXor(Thread* thread, const Int& left, const Int& right);
790
791 // Computes the floor of the quotient of dividing `left` by `right` and
792 // `left` modulo `right` so that `left = quotient * right + modulo`.
793 // Note that this is different from C++ division (which truncates).
794 // Writes the results to the handles pointed to by `quotient` or `modulo`.
795 // It is allowed to specify a nullptr for any of them.
796 // Returns true on success, false on division by zero.
797 bool intDivideModulo(Thread* thread, const Int& dividend, const Int& divisor,
798 Object* quotient, Object* modulo);
799
800 // Returns a copy of `value` with all bits flipped.
801 RawObject intInvert(Thread* thread, const Int& value);
802
803 // Returns the product of `left` and `right`.
804 RawObject intMultiply(Thread* thread, const Int& left, const Int& right);
805
806 // Returns `0 - value`.
807 RawObject intNegate(Thread* thread, const Int& value);
808
809 // Returns the result of subtracting `right` from `left`.
810 RawObject intSubtract(Thread* thread, const Int& left, const Int& right);
811
812 // Converts `num` into a bytes object with the given length. This function
813 // expects the length to be big enough to hold the number and does not check
814 // for overflow.
815 RawObject intToBytes(Thread* thread, const Int& num, word length,
816 endian endianness);
817
818 // Given a possibly invalid LargeInt remove redundant sign- and
819 // zero-extension and convert to a SmallInt when possible.
820 RawObject normalizeLargeInt(Thread* thread, const LargeInt& large_int);
821
822 // Replace the occurences of oldstr get replaced for newstr in src up
823 // to maxcount. If no replacement happens, returns src itself, unmodified.
824 RawObject strReplace(Thread* thread, const Str& src, const Str& oldstr,
825 const Str& newstr, word count);
826
827 void strArrayAddASCII(Thread* thread, const StrArray& array, byte code_point);
828 void strArrayAddCodePoint(Thread* thread, const StrArray& array,
829 int32_t code_point);
830 void strArrayAddStr(Thread* thread, const StrArray& array, const Str& str);
831 void strArrayAddStrArray(Thread* thread, const StrArray& array,
832 const StrArray& str);
833
834 // Ensures that the str array has at least the desired capacity.
835 // Allocates if the existing capacity is insufficient.
836 void strArrayEnsureCapacity(Thread* thread, const StrArray& array,
837 word min_capacity);
838
839 static word nextModuleIndex();
840
841 static int heapOffset() { return OFFSETOF(Runtime, heap_); }
842
843 static int layoutsOffset() { return OFFSETOF(Runtime, layouts_); }
844
845 // Equivalent to `o0 is o1 or o0 == o1` optimized for LargeStr, SmallStr and
846 // SmallInt objects.
847 static RawObject objectEquals(Thread* thread, RawObject o0, RawObject o1);
848
849 // The exec_prefix is a directory prefix where platform-dependent Python files
850 // are installed (e.g. compiled .so files)
851 static wchar_t* execPrefix() { return exec_prefix_; }
852 static void setExecPrefix(const wchar_t* exec_prefix);
853
854 // Getter/setter for the module search path.
855 static wchar_t* moduleSearchPath() { return module_search_path_; }
856 static void setModuleSearchPath(const wchar_t* module_search_path);
857
858 // The prefix is a directory prefix where platform-independent Python files
859 // are installed (e.g. .py library files)
860 static wchar_t* prefix() { return prefix_; }
861 static void setPrefix(const wchar_t* prefix);
862
863 static wchar_t* programName();
864 static void setProgramName(const wchar_t* program_name);
865
866 const byte* hashSecret(size_t size);
867
868 // Sets up the signal handlers.
869 void initializeSignals(Thread* thread, const Module& under_signal);
870
871 void finalizeSignals(Thread* thread);
872
873 RawObject handlePendingSignals(Thread* thread);
874 void setPendingSignal(Thread* thread, int signum);
875
876 RawObject signalCallback(word signum);
877 RawObject setSignalCallback(word signum, const Object& callback);
878
879 bool isFinalizing() { return is_finalizing_; }
880
881 Thread* mainThread() { return main_thread_; }
882
883 void populateEntryAsm(const Function& function);
884
885 bool useBufferedStdio() { return stdio_state_ == StdioState::kBuffered; }
886
887 private:
888 Runtime(word heap_size);
889
890 void initializeHeapTypes(Thread* thread);
891 void initializeInterned(Thread* thread);
892 void initializeJITState();
893 void initializeLayouts();
894 void initializeModules(Thread* thread);
895 void initializePrimitiveInstances();
896 void initializeSymbols(Thread* thread);
897 void initializeTypes(Thread* thread);
898
899 void internSetGrow(Thread* thread);
900
901 void visitRuntimeRoots(PointerVisitor* visitor);
902 void visitThreadRoots(PointerVisitor* visitor);
903
904 word siphash24(View<byte> array);
905
906 RawObject createLargeBytes(word length);
907 RawObject createMutableBytes(word length);
908
909 // Appends attribute entries for fixed attributes to an array of in-object
910 // attribute entries starting at a specific index. Useful for constructing
911 // the in-object attributes array for built-in classes with fixed attributes.
912 void appendBuiltinAttributes(Thread* thread,
913 View<BuiltinAttribute> attributes,
914 const MutableTuple& dst, word start_index);
915
916 // Joins the type's name and attribute's name to produce a qualname
917 RawObject newQualname(Thread* thread, const Type& type, SymbolId name);
918
919 static word immediateHash(RawObject object);
920
921 // Clear all active handle scopes
922 void clearHandleScopes();
923
924 // Clear the allocated memory from all extension related objects
925 void freeApiHandles();
926
927 bool is_finalizing_ = false;
928
929 // The size newCapacity grows to if array is empty. Must be large enough to
930 // guarantee a LargeBytes/LargeStr for Bytearray/StrArray.
931 static const int kInitialEnsuredCapacity = kWordSize * 2;
932 static_assert(kInitialEnsuredCapacity > SmallStr::kMaxLength,
933 "array must be backed by a heap type");
934
935 Heap heap_;
936
937 std::unique_ptr<Interpreter> interpreter_;
938
939 // List of native instances which can be finalizable through tp_dealloc
940 RawObject finalizable_references_ = NoneType::object();
941
942 // A MutableTuple of Layout objects, indexed by layout id.
943 RawObject layouts_ = NoneType::object();
944 // The number of layout objects in layouts_.
945 word num_layouts_ = 0;
946
947 // A Tuple of (A, B, C) triples representing transitions from a layout A to a
948 // class B, resulting in final cached layout C.
949 RawObject layout_type_transitions_ = NoneType::object();
950
951 // The last module ID given out.
952 word max_module_id_ = 0;
953
954 // The ID of builtins module.
955 // TODO(T64005113): Remove this once we mark individual functions.
956 word builtins_module_id_ = -1;
957
958 // Internal-only types, for which the Layout has a different described type
959 RawObject large_bytes_ = NoneType::object();
960 RawObject large_int_ = NoneType::object();
961 RawObject large_str_ = NoneType::object();
962 RawObject small_bytes_ = NoneType::object();
963 RawObject small_int_ = NoneType::object();
964 RawObject small_str_ = NoneType::object();
965
966 // Cached instances
967 RawObject build_class_ = NoneType::object();
968 RawObject display_hook_ = NoneType::object();
969 RawObject ellipsis_ = NoneType::object();
970 RawObject empty_frozen_set_ = NoneType::object();
971 RawObject empty_mutable_bytes_ = NoneType::object();
972 RawObject empty_slice_ = NoneType::object();
973 RawObject empty_tuple_ = NoneType::object();
974 RawObject module_dunder_getattribute_ = NoneType::object();
975 RawObject object_dunder_class_ = NoneType::object();
976 RawObject object_dunder_eq_ = NoneType::object();
977 RawObject object_dunder_getattribute_ = NoneType::object();
978 RawObject object_dunder_hash_ = NoneType::object();
979 RawObject object_dunder_init_ = NoneType::object();
980 RawObject object_dunder_new_ = NoneType::object();
981 RawObject object_dunder_setattr_ = NoneType::object();
982 RawObject str_dunder_eq_ = NoneType::object();
983 RawObject str_dunder_hash_ = NoneType::object();
984 RawObject sys_stderr_ = NoneType::object();
985 RawObject sys_stdin_ = NoneType::object();
986 RawObject sys_stdout_ = NoneType::object();
987 RawObject type_dunder_getattribute_ = NoneType::object();
988
989 RawObject profiling_new_thread_ = NoneType::object();
990 RawObject profiling_call_ = NoneType::object();
991 RawObject profiling_return_ = NoneType::object();
992
993 // Interned strings
994 RawObject interned_ = NoneType::object();
995 word interned_remaining_ = 0;
996
997 // Modules
998 RawObject modules_ = NoneType::object();
999
1000 // C-API State
1001 char capi_state_[kCAPIStateSize];
1002
1003 // Weak reference callback list
1004 RawObject callbacks_ = NoneType::object();
1005
1006 // Quick check if any signals have been tripped.
1007 volatile bool is_signal_pending_ = false;
1008
1009 // Tuple mapping each signal to either SIG_DFL, SIG_IGN, None,
1010 // or a Python object to be called when handling the signal.
1011 RawObject signal_callbacks_ = NoneType::object();
1012
1013 void* signal_stack_ = nullptr;
1014
1015 // File descriptor for writing when a signal is received.
1016 int wakeup_fd_ = -1;
1017
1018 Thread* main_thread_ = nullptr;
1019 Mutex threads_mutex_;
1020
1021 RandomState random_state_;
1022
1023 Symbols* symbols_;
1024
1025 // atexit thunk (to be passed into pylifecycle and called with atexit module)
1026 AtExitFn at_exit_ = nullptr;
1027 void* at_exit_context_ = nullptr;
1028
1029 bool initialized_ = false;
1030
1031 // Non-moving memory for JIT compiled functions.
1032 Space* machine_code_ = nullptr;
1033
1034 static word next_module_index_;
1035
1036 static wchar_t exec_prefix_[];
1037 static wchar_t module_search_path_[];
1038 static wchar_t prefix_[];
1039 static wchar_t program_name_[];
1040
1041 StdioState stdio_state_;
1042
1043 DISALLOW_COPY_AND_ASSIGN(Runtime);
1044};
1045
1046inline RawObject Runtime::emptyMutableBytes() { return empty_mutable_bytes_; }
1047
1048inline RawObject Runtime::emptySlice() { return empty_slice_; }
1049
1050inline RawObject Runtime::emptyTuple() { return empty_tuple_; }
1051
1052inline RawObject Runtime::internStr(Thread* thread, const Object& str) {
1053 if (str.isSmallStr()) {
1054 return *str;
1055 }
1056 return internLargeStr(thread, str);
1057}
1058
1059inline RawObject Runtime::newInt(word value) {
1060 if (SmallInt::isValid(value)) {
1061 return SmallInt::fromWord(value);
1062 }
1063 return newLargeIntFromWord(value);
1064}
1065
1066inline RawObject Runtime::newMutableBytesUninitialized(word size) {
1067 return newMutableBytesZeroed(size);
1068}
1069
1070} // namespace py