xref: /llvm-project/lldb/source/Plugins/ScriptInterpreter/Python/PythonDataObjects.h (revision d9c9da536f0df0efa4dfd95e1797c0edc1950589)
1 //===-- PythonDataObjects.h--------------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #ifndef LLDB_PLUGINS_SCRIPTINTERPRETER_PYTHON_PYTHONDATAOBJECTS_H
11 #define LLDB_PLUGINS_SCRIPTINTERPRETER_PYTHON_PYTHONDATAOBJECTS_H
12 
13 #ifndef LLDB_DISABLE_PYTHON
14 
15 // C Includes
16 // C++ Includes
17 // Other libraries and framework includes
18 // Project includes
19 #include "lldb/lldb-defines.h"
20 #include "lldb/Core/ConstString.h"
21 #include "lldb/Core/StructuredData.h"
22 #include "lldb/Core/Flags.h"
23 #include "lldb/Host/File.h"
24 #include "lldb/Interpreter/OptionValue.h"
25 
26 #include "llvm/ADT/ArrayRef.h"
27 
28 namespace lldb_private {
29 
30 class PythonBytes;
31 class PythonString;
32 class PythonList;
33 class PythonDictionary;
34 class PythonInteger;
35 
36 class StructuredPythonObject : public StructuredData::Generic
37 {
38 public:
39     StructuredPythonObject()
40         : StructuredData::Generic()
41     {
42     }
43 
44     StructuredPythonObject(void *obj)
45         : StructuredData::Generic(obj)
46     {
47         Py_XINCREF(GetValue());
48     }
49 
50     ~StructuredPythonObject() override
51     {
52         if (Py_IsInitialized())
53             Py_XDECREF(GetValue());
54         SetValue(nullptr);
55     }
56 
57     bool
58     IsValid() const override
59     {
60         return GetValue() && GetValue() != Py_None;
61     }
62 
63     void Dump(Stream &s, bool pretty_print = true) const override;
64 
65 private:
66     DISALLOW_COPY_AND_ASSIGN(StructuredPythonObject);
67 };
68 
69 enum class PyObjectType
70 {
71     Unknown,
72     None,
73     Integer,
74     Dictionary,
75     List,
76     String,
77     Bytes,
78     ByteArray,
79     Module,
80     Callable,
81     Tuple,
82     File
83 };
84 
85 enum class PyRefType
86 {
87     Borrowed, // We are not given ownership of the incoming PyObject.
88               // We cannot safely hold it without calling Py_INCREF.
89     Owned     // We have ownership of the incoming PyObject.  We should
90               // not call Py_INCREF.
91 };
92 
93 enum class PyInitialValue
94 {
95     Invalid,
96     Empty
97 };
98 
99 class PythonObject
100 {
101 public:
102     PythonObject()
103         : m_py_obj(nullptr)
104     {
105     }
106 
107     PythonObject(PyRefType type, PyObject *py_obj)
108         : m_py_obj(nullptr)
109     {
110         Reset(type, py_obj);
111     }
112 
113     PythonObject(const PythonObject &rhs)
114         : m_py_obj(nullptr)
115     {
116         Reset(rhs);
117     }
118 
119     virtual ~PythonObject()
120     {
121         Reset();
122     }
123 
124     void
125     Reset()
126     {
127         // Avoid calling the virtual method since it's not necessary
128         // to actually validate the type of the PyObject if we're
129         // just setting to null.
130         if (Py_IsInitialized())
131             Py_XDECREF(m_py_obj);
132         m_py_obj = nullptr;
133     }
134 
135     void
136     Reset(const PythonObject &rhs)
137     {
138         // Avoid calling the virtual method if it's not necessary
139         // to actually validate the type of the PyObject.
140         if (!rhs.IsValid())
141             Reset();
142         else
143             Reset(PyRefType::Borrowed, rhs.m_py_obj);
144     }
145 
146     // PythonObject is implicitly convertible to PyObject *, which will call the
147     // wrong overload.  We want to explicitly disallow this, since a PyObject
148     // *always* owns its reference.  Therefore the overload which takes a
149     // PyRefType doesn't make sense, and the copy constructor should be used.
150     void
151     Reset(PyRefType type, const PythonObject &ref) = delete;
152 
153     virtual void
154     Reset(PyRefType type, PyObject *py_obj)
155     {
156         if (py_obj == m_py_obj)
157             return;
158 
159         if (Py_IsInitialized())
160             Py_XDECREF(m_py_obj);
161 
162         m_py_obj = py_obj;
163 
164         // If this is a borrowed reference, we need to convert it to
165         // an owned reference by incrementing it.  If it is an owned
166         // reference (for example the caller allocated it with PyDict_New()
167         // then we must *not* increment it.
168         if (Py_IsInitialized() && type == PyRefType::Borrowed)
169             Py_XINCREF(m_py_obj);
170     }
171 
172     void
173     Dump () const
174     {
175         if (m_py_obj)
176             _PyObject_Dump (m_py_obj);
177         else
178             puts ("NULL");
179     }
180 
181     void
182     Dump (Stream &strm) const;
183 
184     PyObject*
185     get() const
186     {
187         return m_py_obj;
188     }
189 
190     PyObject*
191     release()
192     {
193         PyObject *result = m_py_obj;
194         m_py_obj = nullptr;
195         return result;
196     }
197 
198     PythonObject &
199     operator=(const PythonObject &other)
200     {
201         Reset(PyRefType::Borrowed, other.get());
202         return *this;
203     }
204 
205     PyObjectType
206     GetObjectType() const;
207 
208     PythonString
209     Repr() const;
210 
211     PythonString
212     Str() const;
213 
214     static PythonObject
215     ResolveNameWithDictionary(llvm::StringRef name, const PythonDictionary &dict);
216 
217     template<typename T>
218     static T
219     ResolveNameWithDictionary(llvm::StringRef name, const PythonDictionary &dict)
220     {
221         return ResolveNameWithDictionary(name, dict).AsType<T>();
222     }
223 
224     PythonObject
225     ResolveName(llvm::StringRef name) const;
226 
227     template<typename T>
228     T
229     ResolveName(llvm::StringRef name) const
230     {
231         return ResolveName(name).AsType<T>();
232     }
233 
234     bool
235     HasAttribute(llvm::StringRef attribute) const;
236 
237     PythonObject
238     GetAttributeValue(llvm::StringRef attribute) const;
239 
240     bool
241     IsValid() const;
242 
243     bool
244     IsAllocated() const;
245 
246     bool
247     IsNone() const;
248 
249     template<typename T>
250     T AsType() const
251     {
252         if (!T::Check(m_py_obj))
253             return T();
254         return T(PyRefType::Borrowed, m_py_obj);
255     }
256 
257     StructuredData::ObjectSP
258     CreateStructuredObject() const;
259 
260 protected:
261     PyObject* m_py_obj;
262 };
263 
264 class PythonBytes : public PythonObject
265 {
266 public:
267     PythonBytes();
268     explicit PythonBytes(llvm::ArrayRef<uint8_t> bytes);
269     PythonBytes(const uint8_t *bytes, size_t length);
270     PythonBytes(PyRefType type, PyObject *o);
271     PythonBytes(const PythonBytes &object);
272 
273     ~PythonBytes() override;
274 
275     static bool
276     Check(PyObject *py_obj);
277 
278     // Bring in the no-argument base class version
279     using PythonObject::Reset;
280 
281     void
282     Reset(PyRefType type, PyObject *py_obj) override;
283 
284     llvm::ArrayRef<uint8_t>
285     GetBytes() const;
286 
287     size_t
288     GetSize() const;
289 
290     void
291     SetBytes(llvm::ArrayRef<uint8_t> stringbytes);
292 
293     StructuredData::StringSP
294     CreateStructuredString() const;
295 };
296 
297 class PythonByteArray : public PythonObject
298 {
299 public:
300     PythonByteArray();
301     explicit PythonByteArray(llvm::ArrayRef<uint8_t> bytes);
302     PythonByteArray(const uint8_t *bytes, size_t length);
303     PythonByteArray(PyRefType type, PyObject *o);
304     PythonByteArray(const PythonBytes &object);
305 
306     ~PythonByteArray() override;
307 
308     static bool
309     Check(PyObject *py_obj);
310 
311     // Bring in the no-argument base class version
312     using PythonObject::Reset;
313 
314     void
315     Reset(PyRefType type, PyObject *py_obj) override;
316 
317     llvm::ArrayRef<uint8_t>
318     GetBytes() const;
319 
320     size_t
321     GetSize() const;
322 
323     void
324     SetBytes(llvm::ArrayRef<uint8_t> stringbytes);
325 
326     StructuredData::StringSP
327     CreateStructuredString() const;
328 };
329 
330 class PythonString : public PythonObject
331 {
332 public:
333     PythonString();
334     explicit PythonString(llvm::StringRef string);
335     explicit PythonString(const char *string);
336     PythonString(PyRefType type, PyObject *o);
337     PythonString(const PythonString &object);
338 
339     ~PythonString() override;
340 
341     static bool Check(PyObject *py_obj);
342 
343     // Bring in the no-argument base class version
344     using PythonObject::Reset;
345 
346     void Reset(PyRefType type, PyObject *py_obj) override;
347 
348     llvm::StringRef
349     GetString() const;
350 
351     size_t
352     GetSize() const;
353 
354     void SetString(llvm::StringRef string);
355 
356     StructuredData::StringSP CreateStructuredString() const;
357 };
358 
359 class PythonInteger : public PythonObject
360 {
361 public:
362     PythonInteger();
363     explicit PythonInteger(int64_t value);
364     PythonInteger(PyRefType type, PyObject *o);
365     PythonInteger(const PythonInteger &object);
366 
367     ~PythonInteger() override;
368 
369     static bool Check(PyObject *py_obj);
370 
371     // Bring in the no-argument base class version
372     using PythonObject::Reset;
373 
374     void Reset(PyRefType type, PyObject *py_obj) override;
375 
376     int64_t GetInteger() const;
377 
378     void
379     SetInteger (int64_t value);
380 
381     StructuredData::IntegerSP CreateStructuredInteger() const;
382 };
383 
384 class PythonList : public PythonObject
385 {
386 public:
387     PythonList() {}
388     explicit PythonList(PyInitialValue value);
389     explicit PythonList(int list_size);
390     PythonList(PyRefType type, PyObject *o);
391     PythonList(const PythonList &list);
392 
393     ~PythonList() override;
394 
395     static bool Check(PyObject *py_obj);
396 
397     // Bring in the no-argument base class version
398     using PythonObject::Reset;
399 
400     void Reset(PyRefType type, PyObject *py_obj) override;
401 
402     uint32_t GetSize() const;
403 
404     PythonObject GetItemAtIndex(uint32_t index) const;
405 
406     void SetItemAtIndex(uint32_t index, const PythonObject &object);
407 
408     void AppendItem(const PythonObject &object);
409 
410     StructuredData::ArraySP CreateStructuredArray() const;
411 };
412 
413 class PythonTuple : public PythonObject
414 {
415 public:
416     PythonTuple() {}
417     explicit PythonTuple(PyInitialValue value);
418     explicit PythonTuple(int tuple_size);
419     PythonTuple(PyRefType type, PyObject *o);
420     PythonTuple(const PythonTuple &tuple);
421     PythonTuple(std::initializer_list<PythonObject> objects);
422     PythonTuple(std::initializer_list<PyObject*> objects);
423 
424     ~PythonTuple() override;
425 
426     static bool Check(PyObject *py_obj);
427 
428     // Bring in the no-argument base class version
429     using PythonObject::Reset;
430 
431     void Reset(PyRefType type, PyObject *py_obj) override;
432 
433     uint32_t GetSize() const;
434 
435     PythonObject GetItemAtIndex(uint32_t index) const;
436 
437     void SetItemAtIndex(uint32_t index, const PythonObject &object);
438 
439     StructuredData::ArraySP CreateStructuredArray() const;
440 };
441 
442 class PythonDictionary : public PythonObject
443 {
444 public:
445     PythonDictionary() {}
446     explicit PythonDictionary(PyInitialValue value);
447     PythonDictionary(PyRefType type, PyObject *o);
448     PythonDictionary(const PythonDictionary &dict);
449 
450     ~PythonDictionary() override;
451 
452     static bool Check(PyObject *py_obj);
453 
454     // Bring in the no-argument base class version
455     using PythonObject::Reset;
456 
457     void Reset(PyRefType type, PyObject *py_obj) override;
458 
459     uint32_t GetSize() const;
460 
461     PythonList GetKeys() const;
462 
463     PythonObject GetItemForKey(const PythonObject &key) const;
464     void SetItemForKey(const PythonObject &key, const PythonObject &value);
465 
466     StructuredData::DictionarySP CreateStructuredDictionary() const;
467 };
468 
469 class PythonModule : public PythonObject
470 {
471   public:
472     PythonModule();
473     PythonModule(PyRefType type, PyObject *o);
474     PythonModule(const PythonModule &dict);
475 
476     ~PythonModule() override;
477 
478     static bool Check(PyObject *py_obj);
479 
480     static PythonModule
481     BuiltinsModule();
482 
483     static PythonModule
484     MainModule();
485 
486     static PythonModule
487     AddModule(llvm::StringRef module);
488 
489     static PythonModule
490     ImportModule(llvm::StringRef module);
491 
492     // Bring in the no-argument base class version
493     using PythonObject::Reset;
494 
495     void Reset(PyRefType type, PyObject *py_obj) override;
496 
497     PythonDictionary GetDictionary() const;
498 };
499 
500 class PythonCallable : public PythonObject
501 {
502 public:
503     struct ArgInfo {
504         size_t count;
505         bool is_bound_method : 1;
506         bool has_varargs : 1;
507         bool has_kwargs : 1;
508     };
509 
510     PythonCallable();
511     PythonCallable(PyRefType type, PyObject *o);
512     PythonCallable(const PythonCallable &dict);
513 
514     ~PythonCallable() override;
515 
516     static bool
517     Check(PyObject *py_obj);
518 
519     // Bring in the no-argument base class version
520     using PythonObject::Reset;
521 
522     void
523     Reset(PyRefType type, PyObject *py_obj) override;
524 
525     ArgInfo
526     GetNumArguments() const;
527 
528     PythonObject
529     operator ()();
530 
531     PythonObject
532     operator ()(std::initializer_list<PyObject*> args);
533 
534     PythonObject
535     operator ()(std::initializer_list<PythonObject> args);
536 
537     template<typename Arg, typename... Args>
538     PythonObject
539     operator ()(const Arg &arg, Args... args)
540     {
541         return operator()({ arg, args... });
542     }
543 };
544 
545 
546 class PythonFile : public PythonObject
547 {
548   public:
549     PythonFile();
550     PythonFile(File &file, const char *mode);
551     PythonFile(const char *path, const char *mode);
552     PythonFile(PyRefType type, PyObject *o);
553 
554     ~PythonFile() override;
555 
556     static bool Check(PyObject *py_obj);
557 
558     using PythonObject::Reset;
559 
560     void Reset(PyRefType type, PyObject *py_obj) override;
561     void Reset(File &file, const char *mode);
562 
563     static uint32_t GetOptionsFromMode(llvm::StringRef mode);
564 
565     bool GetUnderlyingFile(File &file) const;
566 };
567 
568 } // namespace lldb_private
569 
570 #endif
571 
572 #endif // LLDB_PLUGINS_SCRIPTINTERPRETER_PYTHON_PYTHONDATAOBJECTS_H
573