forked from M-Labs/artiq
runtime: support clock switching
This commit is contained in:
parent
94218f785e
commit
fc690ead75
@ -7,6 +7,7 @@ from fractions import Fraction
|
||||
import logging
|
||||
|
||||
from artiq.language import core as core_language
|
||||
from artiq.language import units
|
||||
from artiq.coredevice.runtime import Environment
|
||||
from artiq.coredevice import runtime_exceptions
|
||||
|
||||
@ -23,6 +24,7 @@ class _H2DMsgType(Enum):
|
||||
LOAD_OBJECT = 2
|
||||
RUN_KERNEL = 3
|
||||
SET_BAUD_RATE = 4
|
||||
SWITCH_CLOCK = 5
|
||||
|
||||
|
||||
class _D2HMsgType(Enum):
|
||||
@ -37,6 +39,8 @@ class _D2HMsgType(Enum):
|
||||
KERNEL_EXCEPTION = 9
|
||||
KERNEL_STARTUP_FAILED = 10
|
||||
RPC_REQUEST = 11
|
||||
CLOCK_SWITCH_COMPLETED = 12
|
||||
CLOCK_SWITCH_FAILED = 13
|
||||
|
||||
|
||||
def _write_exactly(f, data):
|
||||
@ -135,12 +139,21 @@ class Comm:
|
||||
runtime_id += chr(reply)
|
||||
if runtime_id != "AROR":
|
||||
raise UnsupportedDevice("Unsupported runtime ID: "+runtime_id)
|
||||
(ref_freq_i, ref_freq_fn, ref_freq_fd) = struct.unpack(
|
||||
ref_freq_i, ref_freq_fn, ref_freq_fd = struct.unpack(
|
||||
">lBB", _read_exactly(self.port, 6))
|
||||
ref_period = 1/(ref_freq_i + Fraction(ref_freq_fn, ref_freq_fd))
|
||||
ref_freq = (ref_freq_i + Fraction(ref_freq_fn, ref_freq_fd))*units.Hz
|
||||
ref_period = 1/ref_freq
|
||||
logger.debug("environment ref_period: {}".format(ref_period))
|
||||
return Environment(ref_period)
|
||||
|
||||
def switch_clock(self, external):
|
||||
_write_exactly(self.port, struct.pack(
|
||||
">lbb", 0x5a5a5a5a, _H2DMsgType.SWITCH_CLOCK.value,
|
||||
int(external)))
|
||||
msg = self._get_device_msg()
|
||||
if msg != _D2HMsgType.CLOCK_SWITCH_COMPLETED:
|
||||
raise IOError("Incorrect reply from device: "+str(msg))
|
||||
|
||||
def load(self, kcode):
|
||||
_write_exactly(self.port, struct.pack(
|
||||
">lblL",
|
||||
|
@ -42,13 +42,20 @@ def _no_debug_unparse(label, node):
|
||||
|
||||
|
||||
class Core:
|
||||
def __init__(self, comm, runtime_env=None):
|
||||
def __init__(self, comm, external_clock=None, runtime_env=None):
|
||||
if runtime_env is None:
|
||||
runtime_env = comm.get_runtime_env()
|
||||
self.runtime_env = runtime_env
|
||||
self.comm = comm
|
||||
self.core = self
|
||||
|
||||
if external_clock is None:
|
||||
self.ref_period = self.runtime_env.internal_ref_period
|
||||
self.comm.switch_clock(False)
|
||||
else:
|
||||
self.ref_period = external_clock
|
||||
self.comm.switch_clock(True)
|
||||
|
||||
def transform_stack(self, func_def, rpc_map, exception_map,
|
||||
debug_unparse=_no_debug_unparse):
|
||||
lower_units(func_def, rpc_map)
|
||||
@ -57,7 +64,7 @@ class Core:
|
||||
remove_inter_assigns(func_def)
|
||||
debug_unparse("remove_inter_assigns_1", func_def)
|
||||
|
||||
quantize_time(func_def, self.runtime_env.ref_period)
|
||||
quantize_time(func_def, self.ref_period.amount)
|
||||
debug_unparse("quantize_time", func_def)
|
||||
|
||||
fold_constants(func_def)
|
||||
@ -69,7 +76,7 @@ class Core:
|
||||
interleave(func_def)
|
||||
debug_unparse("interleave", func_def)
|
||||
|
||||
lower_time(func_def, self.runtime_env.initial_time)
|
||||
lower_time(func_def, self.runtime_env.warmup_time/self.ref_period)
|
||||
debug_unparse("lower_time", func_def)
|
||||
|
||||
remove_inter_assigns(func_def)
|
||||
|
@ -141,11 +141,11 @@ def _debug_dump_obj(obj):
|
||||
|
||||
|
||||
class Environment(LinkInterface):
|
||||
def __init__(self, ref_period):
|
||||
def __init__(self, internal_ref_period):
|
||||
self.cpu_type = "or1k"
|
||||
self.ref_period = ref_period
|
||||
self.internal_ref_period = internal_ref_period
|
||||
# allow 1ms for all initial DDS programming
|
||||
self.initial_time = int(Fraction(1, 1000)/self.ref_period)
|
||||
self.warmup_time = 1*units.ms
|
||||
|
||||
def emit_object(self):
|
||||
tm = lt.TargetMachine.new(triple=self.cpu_type, cpu="generic")
|
||||
@ -155,4 +155,4 @@ class Environment(LinkInterface):
|
||||
|
||||
def __repr__(self):
|
||||
return "<Environment {} {}>".format(self.cpu_type,
|
||||
str(units.Hz/self.ref_period))
|
||||
str(1/self.ref_period))
|
||||
|
@ -11,6 +11,7 @@ enum {
|
||||
MSGTYPE_LOAD_OBJECT,
|
||||
MSGTYPE_RUN_KERNEL,
|
||||
MSGTYPE_SET_BAUD_RATE,
|
||||
MSGTYPE_SWITCH_CLOCK,
|
||||
};
|
||||
|
||||
/* device to host */
|
||||
@ -30,6 +31,9 @@ enum {
|
||||
MSGTYPE_KERNEL_STARTUP_FAILED,
|
||||
|
||||
MSGTYPE_RPC_REQUEST,
|
||||
|
||||
MSGTYPE_CLOCK_SWITCH_COMPLETED,
|
||||
MSGTYPE_CLOCK_SWITCH_FAILED,
|
||||
};
|
||||
|
||||
static int receive_int(void)
|
||||
@ -169,6 +173,9 @@ void comm_serve(object_loader load_object, kernel_runner run_kernel)
|
||||
send_int(0x5a5a5a5a);
|
||||
uart_sync();
|
||||
uart_tuning_word_write(ftw);
|
||||
} else if(msgtype == MSGTYPE_SWITCH_CLOCK) {
|
||||
rtiocrg_clock_sel_write(receive_char());
|
||||
send_char(MSGTYPE_CLOCK_SWITCH_COMPLETED);
|
||||
} else
|
||||
send_char(MSGTYPE_MESSAGE_UNRECOGNIZED);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user