Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Menu
Open sidebar
TASTE
uPython-mirror
Commits
fb083ea9
Commit
fb083ea9
authored
Feb 01, 2014
by
Damien George
Browse files
py: mp_execute_byte_code has 2 arg arrays, for more efficient default params.
parent
87413a4d
Changes
4
Hide whitespace changes
Inline
Side-by-side
py/bc.h
View file @
fb083ea9
mp_obj_t
mp_execute_byte_code
(
const
byte
*
code
,
const
mp_obj_t
*
args
,
uint
n_args
,
uint
n_state
);
mp_obj_t
mp_execute_byte_code
(
const
byte
*
code
,
const
mp_obj_t
*
args
,
uint
n_args
,
const
mp_obj_t
*
args2
,
uint
n_args2
,
uint
n_state
);
bool
mp_execute_byte_code_2
(
const
byte
*
code_info
,
const
byte
**
ip_in_out
,
mp_obj_t
*
fastn
,
mp_obj_t
**
sp_in_out
);
void
mp_byte_code_print
(
const
byte
*
code
,
int
len
);
py/emitbc.c
View file @
fb083ea9
...
...
@@ -107,6 +107,22 @@ static void emit_write_byte_code_byte_byte(emit_t* emit, byte b1, uint b2) {
c
[
1
]
=
b2
;
}
static
void
emit_write_byte_code_uint
(
emit_t
*
emit
,
uint
num
)
{
if
(
num
<=
127
)
{
// fits in 0x7f
// fit argument in single byte
byte
*
c
=
emit_get_cur_to_write_byte_code
(
emit
,
1
);
c
[
0
]
=
num
;
}
else
if
(
num
<=
16383
)
{
// fits in 0x3fff
// fit argument in two bytes
byte
*
c
=
emit_get_cur_to_write_byte_code
(
emit
,
2
);
c
[
0
]
=
(
num
>>
8
)
|
0x80
;
c
[
1
]
=
num
;
}
else
{
// larger numbers not implemented/supported
assert
(
0
);
}
}
// integers (for small ints) are stored as 24 bits, in excess
static
void
emit_write_byte_code_byte_int
(
emit_t
*
emit
,
byte
b1
,
machine_int_t
num
)
{
num
+=
0x800000
;
...
...
@@ -118,26 +134,21 @@ static void emit_write_byte_code_byte_int(emit_t* emit, byte b1, machine_int_t n
c
[
3
]
=
num
>>
16
;
}
static
void
emit_write_byte_code_byte_uint
(
emit_t
*
emit
,
byte
b1
,
uint
num
)
{
if
(
num
<=
127
)
{
// fits in 0x7f
// fit argument in single byte
byte
*
c
=
emit_get_cur_to_write_byte_code
(
emit
,
2
);
c
[
0
]
=
b1
;
c
[
1
]
=
num
;
}
else
if
(
num
<=
16383
)
{
// fits in 0x3fff
// fit argument in two bytes
byte
*
c
=
emit_get_cur_to_write_byte_code
(
emit
,
3
);
c
[
0
]
=
b1
;
c
[
1
]
=
(
num
>>
8
)
|
0x80
;
c
[
2
]
=
num
;
}
else
{
// larger numbers not implemented/supported
assert
(
0
);
}
static
void
emit_write_byte_code_byte_uint
(
emit_t
*
emit
,
byte
b
,
uint
num
)
{
emit_write_byte_code_byte
(
emit
,
b
);
emit_write_byte_code_uint
(
emit
,
num
);
}
static
void
emit_write_byte_code_byte_qstr
(
emit_t
*
emit
,
byte
b1
,
qstr
qstr
)
{
emit_write_byte_code_byte_uint
(
emit
,
b1
,
qstr
);
/* currently unused
static void emit_write_byte_code_byte_uint_uint(emit_t* emit, byte b, uint num1, uint num2) {
emit_write_byte_code_byte(emit, b);
emit_write_byte_code_byte_uint(emit, num1);
emit_write_byte_code_byte_uint(emit, num2);
}
*/
static
void
emit_write_byte_code_byte_qstr
(
emit_t
*
emit
,
byte
b
,
qstr
qstr
)
{
emit_write_byte_code_byte_uint
(
emit
,
b
,
qstr
);
}
// unsigned labels are relative to ip following this instruction, stored as 16 bits
...
...
@@ -665,13 +676,13 @@ static void emit_bc_unpack_ex(emit_t *emit, int n_left, int n_right) {
static
void
emit_bc_make_function
(
emit_t
*
emit
,
scope_t
*
scope
,
int
n_dict_params
,
int
n_default_params
)
{
assert
(
n_dict_params
==
0
);
if
(
n_default_params
!=
0
)
{
if
(
n_default_params
==
0
)
{
emit_pre
(
emit
,
1
);
emit_write_byte_code_byte_uint
(
emit
,
MP_BC_MAKE_FUNCTION
,
scope
->
unique_code_id
);
}
else
{
emit_bc_build_tuple
(
emit
,
n_default_params
);
emit_pre
(
emit
,
0
);
emit_write_byte_code_byte_uint
(
emit
,
MP_BC_MAKE_FUNCTION_DEFARGS
,
scope
->
unique_code_id
);
}
else
{
emit_pre
(
emit
,
1
);
emit_write_byte_code_byte_uint
(
emit
,
MP_BC_MAKE_FUNCTION
,
scope
->
unique_code_id
);
}
}
...
...
py/objfun.c
View file @
fb083ea9
...
...
@@ -154,26 +154,13 @@ mp_obj_t fun_bc_call(mp_obj_t self_in, uint n_args, uint n_kw, const mp_obj_t *a
nlr_jump
(
mp_obj_new_exception_msg
(
MP_QSTR_TypeError
,
"function does not take keyword arguments"
));
}
mp_obj_t
full_args
[
n_args
];
if
(
n_args
<
self
->
n_args
)
{
memcpy
(
full_args
,
args
,
n_args
*
sizeof
(
*
args
));
int
use_def_args
=
self
->
n_args
-
n_args
;
memcpy
(
full_args
+
n_args
,
self
->
def_args
+
self
->
n_def_args
-
use_def_args
,
use_def_args
*
sizeof
(
*
args
));
args
=
full_args
;
n_args
=
self
->
n_args
;
}
// optimisation: allow the compiler to optimise this tail call for
// the common case when the globals don't need to be changed
uint
use_def_args
=
self
->
n_args
-
n_args
;
mp_map_t
*
old_globals
=
rt_globals_get
();
if
(
self
->
globals
==
old_globals
)
{
return
mp_execute_byte_code
(
self
->
bytecode
,
args
,
n_args
,
self
->
n_state
);
}
else
{
rt_globals_set
(
self
->
globals
);
mp_obj_t
result
=
mp_execute_byte_code
(
self
->
bytecode
,
args
,
n_args
,
self
->
n_state
);
rt_globals_set
(
old_globals
);
return
result
;
}
rt_globals_set
(
self
->
globals
);
mp_obj_t
result
=
mp_execute_byte_code
(
self
->
bytecode
,
args
,
n_args
,
self
->
def_args
+
self
->
n_def_args
-
use_def_args
,
use_def_args
,
self
->
n_state
);
rt_globals_set
(
old_globals
);
return
result
;
}
const
mp_obj_type_t
fun_bc_type
=
{
...
...
py/vm.c
View file @
fb083ea9
...
...
@@ -46,7 +46,7 @@ typedef enum {
#define TOP() (*sp)
#define SET_TOP(val) *sp = (val)
mp_obj_t
mp_execute_byte_code
(
const
byte
*
code
,
const
mp_obj_t
*
args
,
uint
n_args
,
uint
n_state
)
{
mp_obj_t
mp_execute_byte_code
(
const
byte
*
code
,
const
mp_obj_t
*
args
,
uint
n_args
,
const
mp_obj_t
*
args2
,
uint
n_args2
,
uint
n_state
)
{
// allocate state for locals and stack
mp_obj_t
temp_state
[
10
];
mp_obj_t
*
state
=
&
temp_state
[
0
];
...
...
@@ -56,10 +56,12 @@ mp_obj_t mp_execute_byte_code(const byte *code, const mp_obj_t *args, uint n_arg
mp_obj_t
*
sp
=
&
state
[
0
]
-
1
;
// init args
for
(
int
i
=
0
;
i
<
n_args
;
i
++
)
{
assert
(
i
<
8
);
for
(
uint
i
=
0
;
i
<
n_args
;
i
++
)
{
state
[
n_state
-
1
-
i
]
=
args
[
i
];
}
for
(
uint
i
=
0
;
i
<
n_args2
;
i
++
)
{
state
[
n_state
-
1
-
n_args
-
i
]
=
args2
[
i
];
}
const
byte
*
ip
=
code
;
...
...
@@ -71,7 +73,7 @@ mp_obj_t mp_execute_byte_code(const byte *code, const mp_obj_t *args, uint n_arg
{
for
(
uint
n_local
=
*
ip
++
;
n_local
>
0
;
n_local
--
)
{
uint
local_num
=
*
ip
++
;
if
(
local_num
<
n_args
)
{
if
(
local_num
<
n_args
+
n_args2
)
{
state
[
n_state
-
1
-
local_num
]
=
mp_obj_new_cell
(
state
[
n_state
-
1
-
local_num
]);
}
else
{
state
[
n_state
-
1
-
local_num
]
=
mp_obj_new_cell
(
MP_OBJ_NULL
);
...
...
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment