9
9
#include "pycore_opcode.h" // _PyOpcode_Deopt
10
10
#include "pycore_pystate.h" // _PyInterpreterState_GET()
11
11
#include "pycore_tuple.h" // _PyTuple_ITEMS()
12
+ #include "pycore_ceval.h" // _PyTuple_ITEMS()
12
13
#include "clinic/codeobject.c.h"
13
14
15
+ #include <stdio.h>
16
+ #include <stdlib.h>
17
+ #include <sys/mman.h>
18
+ #include <stdio.h>
19
+ #include <unistd.h>
20
+
21
+ #include <sys/types.h>
22
+ #include <stdio.h>
23
+ #include <stdlib.h>
24
+ #include <errno.h>
25
+
26
+
27
+
14
28
15
29
/******************
16
30
* generic helpers
@@ -286,6 +300,101 @@ _PyCode_Validate(struct _PyCodeConstructor *con)
286
300
return 0 ;
287
301
}
288
302
303
+ py_trampoline compile_blech (void ) {
304
+ char * memory = mmap (NULL , // address
305
+ 4096 , // size
306
+ PROT_READ | PROT_WRITE | PROT_EXEC ,
307
+ MAP_PRIVATE | MAP_ANONYMOUS ,
308
+ -1 , // fd (not used here)
309
+ 0 ); // offset (not used here)
310
+ if (!memory ) {
311
+ perror ("failed to allocate memory" );
312
+ exit (1 );
313
+ }
314
+
315
+ int i = 0 ;
316
+
317
+ memory [i ++ ] = 0x55 ;
318
+ memory [i ++ ] = 0x48 ;
319
+ memory [i ++ ] = 0x89 ;
320
+ memory [i ++ ] = 0xe5 ;
321
+ memory [i ++ ] = 0x48 ;
322
+ memory [i ++ ] = 0x83 ;
323
+ memory [i ++ ] = 0xec ;
324
+ memory [i ++ ] = 0x20 ;
325
+ memory [i ++ ] = 0x48 ;
326
+ memory [i ++ ] = 0x89 ;
327
+ memory [i ++ ] = 0x7d ;
328
+ memory [i ++ ] = 0xf8 ;
329
+ memory [i ++ ] = 0x48 ;
330
+ memory [i ++ ] = 0x89 ;
331
+ memory [i ++ ] = 0x75 ;
332
+ memory [i ++ ] = 0xf0 ;
333
+ memory [i ++ ] = 0x48 ;
334
+ memory [i ++ ] = 0x89 ;
335
+ memory [i ++ ] = 0x55 ;
336
+ memory [i ++ ] = 0xe8 ;
337
+ memory [i ++ ] = 0x89 ;
338
+ memory [i ++ ] = 0x4d ;
339
+ memory [i ++ ] = 0xe4 ;
340
+ memory [i ++ ] = 0x8b ;
341
+ memory [i ++ ] = 0x55 ;
342
+ memory [i ++ ] = 0xe4 ;
343
+ memory [i ++ ] = 0x48 ;
344
+ memory [i ++ ] = 0x8b ;
345
+ memory [i ++ ] = 0x4d ;
346
+ memory [i ++ ] = 0xe8 ;
347
+ memory [i ++ ] = 0x48 ;
348
+ memory [i ++ ] = 0x8b ;
349
+ memory [i ++ ] = 0x45 ;
350
+ memory [i ++ ] = 0xf0 ;
351
+ memory [i ++ ] = 0x4c ;
352
+ memory [i ++ ] = 0x8b ;
353
+ memory [i ++ ] = 0x45 ;
354
+ memory [i ++ ] = 0xf8 ;
355
+ memory [i ++ ] = 0x48 ;
356
+ memory [i ++ ] = 0x89 ;
357
+ memory [i ++ ] = 0xce ;
358
+ memory [i ++ ] = 0x48 ;
359
+ memory [i ++ ] = 0x89 ;
360
+ memory [i ++ ] = 0xc7 ;
361
+ memory [i ++ ] = 0x41 ;
362
+ memory [i ++ ] = 0xff ;
363
+ memory [i ++ ] = 0xd0 ;
364
+ memory [i ++ ] = 0xc9 ;
365
+ memory [i ++ ] = 0xc3 ;
366
+
367
+ return (py_trampoline ) memory ;
368
+ }
369
+
370
+ FILE * perf_map_open (pid_t pid ) {
371
+ char filename [500 ];
372
+ snprintf (filename , sizeof (filename ), "/tmp/perf-%d.map" , pid );
373
+ FILE * res = fopen (filename , "a" );
374
+ if (!res ) {
375
+ fprintf (stderr , "Couldn't open %s: errno(%d)" , filename , errno );
376
+ exit (0 );
377
+ }
378
+ return res ;
379
+ }
380
+
381
+ int perf_map_close (FILE * fp ) {
382
+ if (fp )
383
+ return fclose (fp );
384
+ else
385
+ return 0 ;
386
+ }
387
+
388
+ void perf_map_write_entry (FILE * method_file , const void * code_addr , unsigned int code_size , const char * entry ) {
389
+ fprintf (method_file , "%lx %x %s\n" , (unsigned long ) code_addr , code_size , entry );
390
+ }
391
+
392
+ typedef PyObject * (* py_evaluator )(PyThreadState * , _PyInterpreterFrame * , int throwflag );
393
+
394
+ PyObject * the_trampoline (py_evaluator eval , PyThreadState * t , _PyInterpreterFrame * f , int p ) {
395
+ return eval (t , f ,p );
396
+ }
397
+
289
398
static void
290
399
init_code (PyCodeObject * co , struct _PyCodeConstructor * con )
291
400
{
@@ -300,6 +409,13 @@ init_code(PyCodeObject *co, struct _PyCodeConstructor *con)
300
409
co -> co_name = con -> name ;
301
410
Py_INCREF (con -> qualname );
302
411
co -> co_qualname = con -> qualname ;
412
+
413
+ py_trampoline f = compile_blech ();
414
+ FILE * pfile = perf_map_open (getpid ());
415
+ perf_map_write_entry (pfile , f , 4096 , PyUnicode_AsUTF8 (con -> qualname ));
416
+ perf_map_close (pfile );
417
+
418
+ co -> co_trampoline = f ;
303
419
co -> co_flags = con -> flags ;
304
420
305
421
co -> co_firstlineno = con -> firstlineno ;
0 commit comments