├── .gitignore ├── test ├── Targets │ ├── u_series.xc.expect │ ├── multicore_l2.xc.expect │ ├── multicore_line.xc.expect │ ├── u_series.xc │ ├── multicore_l2.xc │ ├── multicore_line.xc │ └── u_series.xc.xn ├── helloworld.c.expect ├── SystemCalls │ ├── overlays.xc.expect │ ├── is_simulation.S │ ├── argv_xs2.c │ ├── overlays.xc │ ├── io.c │ ├── files.c │ └── argv.S ├── Exceptions │ ├── trap_info.S.expect │ ├── ecall.S │ ├── trap_info.S │ ├── kcall.S │ ├── illegal_resource.S │ └── arithmetic.S ├── basic.c ├── Options │ ├── max_cycles.xc │ ├── warn_packet_overtake.xc │ ├── multi_loopback.xc │ └── port_arguments.xc ├── lit.site.cfg.in ├── elf_entry_point.S ├── helloworld.c ├── Instructions │ ├── GETSR.S │ ├── LDAPB.c │ ├── LDAPF.c │ ├── BLACP.S │ ├── BLAT.S │ ├── BLA.S │ └── xor4.c ├── Resources │ ├── Ports │ │ ├── ignored_output.xc │ │ ├── timestamp.xc │ │ ├── peek.xc │ │ ├── outclock.xc │ │ ├── timed2.xc │ │ ├── timed.xc │ │ ├── buffered.xc │ │ ├── timing2.xc │ │ ├── buffered2.xc │ │ ├── timing.xc │ │ ├── partial_output.xc │ │ ├── readyOut.xc │ │ ├── partial_input_timed.xc │ │ ├── readyIn.xc │ │ ├── partial_input.xc │ │ ├── readyOut2.xc │ │ ├── timed_direction_change.xc │ │ ├── port_counter.xc │ │ ├── buffered_timed_conditional.xc │ │ ├── port_counter3.xc │ │ ├── buffered_conditional.xc │ │ ├── port_counter2.xc │ │ ├── setpsc.xc │ │ ├── set_port_inv.xc │ │ ├── readyOut3.xc │ │ ├── hold_event_value.S │ │ ├── uart2.xc │ │ ├── handshaken.xc │ │ ├── uart.xc │ │ ├── events.xc │ │ ├── setpsc_output.xc │ │ └── multicore.xc │ ├── ClockBlocks │ │ ├── port_source5.xc │ │ ├── port_source4.xc │ │ ├── port_source3.xc │ │ ├── port_source2.xc │ │ └── port_source.xc │ ├── paused_on.xc │ ├── Threads │ │ └── unsynchronised.S │ └── Chanends │ │ ├── pause.S │ │ ├── not_in_use_junk.S │ │ ├── ownership.S │ │ └── basic.S ├── SelfModiyingCode │ └── basic.S ├── Peripherals │ └── uart.xc ├── fibonacci.c ├── Interrupts │ ├── kernel.S │ └── interrupt.S └── fibonacci.c.expect ├── thirdparty └── lit │ ├── lit │ ├── ExampleTests │ │ ├── pass.c │ │ ├── LLVM.OutOfTree │ │ │ ├── obj │ │ │ │ └── test │ │ │ │ │ ├── Foo │ │ │ │ │ └── lit.local.cfg │ │ │ │ │ └── lit.site.cfg │ │ │ ├── src │ │ │ │ └── test │ │ │ │ │ └── Foo │ │ │ │ │ ├── data.txt │ │ │ │ │ ├── pct-S.ll │ │ │ │ │ └── dg.exp │ │ │ └── lit.local.cfg │ │ ├── xfail.c │ │ ├── xpass.c │ │ ├── fail.c │ │ ├── TclTest │ │ │ ├── stderr-pipe.ll │ │ │ ├── lit.local.cfg │ │ │ └── tcl-redir-1.ll │ │ ├── required-and-present.c │ │ ├── LLVM.InTree │ │ │ └── test │ │ │ │ ├── Bar │ │ │ │ ├── bar-test.ll │ │ │ │ └── dg.exp │ │ │ │ └── lit.site.cfg │ │ ├── ShExternal │ │ │ └── lit.local.cfg │ │ ├── ShInternal │ │ │ └── lit.local.cfg │ │ ├── required-and-missing.c │ │ ├── Clang │ │ │ ├── fsyntax-only.c │ │ │ └── lit.cfg │ │ └── lit.cfg │ ├── LitFormats.py │ ├── __init__.py │ ├── ExampleTests.ObjDir │ │ └── lit.site.cfg │ └── LitTestCase.py │ ├── lit.py │ ├── TODO │ ├── setup.py │ └── LICENSE.TXT ├── utils ├── not │ ├── CMakeLists.txt │ └── not.cpp ├── genHex │ ├── CMakeLists.txt │ └── genHex.c ├── instgen │ └── CMakeLists.txt └── genJitGlobalMap │ ├── CMakeLists.txt │ └── genJitGlobalMap.cpp ├── Version.txt ├── lib ├── WatchpointException.cpp ├── AXEVersion.h.in ├── NetworkLink.cpp ├── Peripheral.cpp ├── PortInterface.cpp ├── PortSignalTracker.cpp ├── InstructionProperties.cpp ├── InstructionTraceInfo.cpp ├── Timeout.cpp ├── AXEInitialize.h ├── Array.h ├── Peripheral.h ├── registerAllPeripherals.h ├── Compiler.h ├── Timeout.h ├── SDRAM.h ├── SPIFlash.h ├── UartRx.h ├── JitGlobalMap.h ├── LCDScreen.h ├── PS2Keyboard.h ├── EthernetPhy.h ├── InstructionBitcode.h ├── PortHandleClockProxy.cpp ├── NetworkLinkTapDefault.cpp ├── PortNames.h ├── InstructionTraceInfo.h ├── TrapInfo.h ├── PortAliases.cpp ├── XNTransform.xslt ├── InstructionBitcode.cpp ├── Register.cpp ├── PeripheralNode.h ├── Runnable.h ├── InstFunction.h ├── PortSignalTracker.h ├── JitGlobalMap.cpp ├── WatchpointException.h ├── XEReader.h ├── XMLUtils.h ├── Exceptions.h ├── LoadedElf.h ├── LLVMExtra.h ├── NetworkLink.h ├── PortHandleClockProxy.h ├── WatchpointManager.cpp ├── Range.h ├── BreakpointManager.h ├── PortAliases.h ├── PeripheralRegistry.h ├── LoadedElf.cpp ├── AccessSecondIterator.h ├── Exceptions.cpp ├── JIT.h ├── RunnableQueue.cpp ├── SDLEventPoller.h ├── Lock.cpp ├── Register.h ├── Property.cpp ├── SSwitchCtrlRegs.h ├── AXEInitialize.cpp ├── PortCombiner.h ├── SystemStateWrapper.h ├── PortSplitter.h ├── CRC.h ├── StopReason.cpp ├── registerAllPeripherals.cpp ├── BreakpointManager.cpp ├── PeripheralRegistry.cpp ├── ChanEndpoint.cpp ├── SystemStateWrapper.cpp ├── PortInterface.h ├── PeripheralDescriptor.cpp ├── Instruction.h ├── SDLEventPoller.cpp ├── Lock.h ├── Token.h ├── PeripheralNode.cpp ├── PortCombiner.cpp ├── PortArg.h ├── InstructionHelpers.h ├── RunnableQueue.h ├── StatsTracer.h ├── StopReason.h ├── CheckPacketOvertakeTracer.h ├── ProcessorNode.h ├── WatchpointManager.h ├── Config.h.in ├── Endianness.h ├── BootSequencer.h ├── InstructionOpcode.h ├── Timer.h ├── InstructionMacrosCommon.h ├── JITOptimize.h ├── InstructionProperties.h ├── XMLUtils.cpp ├── Tracer.cpp ├── StatsTracer.cpp ├── SSwitch.h ├── Synchroniser.cpp └── PortSplitter.cpp ├── tools └── axe │ ├── CMakeLists.txt │ └── Options.h ├── benchmarks └── dhry_main.xc ├── cmake └── Modules │ ├── FindLibRt.cmake │ ├── FindClang.cmake │ ├── FindLibElf.cmake │ └── FindSDL2.cmake ├── .travis.yml └── NETWORK.rst /.gitignore: -------------------------------------------------------------------------------- 1 | *.pyc 2 | -------------------------------------------------------------------------------- /test/Targets/u_series.xc.expect: -------------------------------------------------------------------------------- 1 | hello 2 | -------------------------------------------------------------------------------- /test/helloworld.c.expect: -------------------------------------------------------------------------------- 1 | Hello world 2 | -------------------------------------------------------------------------------- /test/SystemCalls/overlays.xc.expect: -------------------------------------------------------------------------------- 1 | f 2 | g 3 | -------------------------------------------------------------------------------- /test/Targets/multicore_l2.xc.expect: -------------------------------------------------------------------------------- 1 | hello 2 | hello 3 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/pass.c: -------------------------------------------------------------------------------- 1 | // RUN: true 2 | -------------------------------------------------------------------------------- /utils/not/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(not not.cpp) 2 | -------------------------------------------------------------------------------- /test/Exceptions/trap_info.S.expect: -------------------------------------------------------------------------------- 1 | Unhandled exception: foo 2 | -------------------------------------------------------------------------------- /utils/genHex/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(genHex genHex.c) 2 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.OutOfTree/obj/test/Foo/lit.local.cfg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/xfail.c: -------------------------------------------------------------------------------- 1 | // RUN: false 2 | // XFAIL: * 3 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/xpass.c: -------------------------------------------------------------------------------- 1 | // RUN: true 2 | // XFAIL 3 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.OutOfTree/src/test/Foo/data.txt: -------------------------------------------------------------------------------- 1 | hi 2 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.OutOfTree/lit.local.cfg: -------------------------------------------------------------------------------- 1 | config.excludes = ['src'] 2 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/fail.c: -------------------------------------------------------------------------------- 1 | // RUN: echo 'I am some stdout' 2 | // RUN: false 3 | -------------------------------------------------------------------------------- /Version.txt: -------------------------------------------------------------------------------- 1 | set(AXE_VERSION_MAJOR 0) 2 | set(AXE_VERSION_MINOR 2) 3 | set(AXE_VERSION_TWEAK "-git") 4 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.OutOfTree/src/test/Foo/pct-S.ll: -------------------------------------------------------------------------------- 1 | ; RUN: grep "hi" %S/data.txt 2 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/TclTest/stderr-pipe.ll: -------------------------------------------------------------------------------- 1 | ; RUN: gcc -### > /dev/null |& grep {gcc version} 2 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/required-and-present.c: -------------------------------------------------------------------------------- 1 | // RUN: true 2 | // REQUIRES: some-feature-name 3 | -------------------------------------------------------------------------------- /test/Targets/multicore_line.xc.expect: -------------------------------------------------------------------------------- 1 | hello 2 | hello 3 | hello 4 | hello 5 | hello 6 | hello 7 | hello 8 | hello 9 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.InTree/test/Bar/bar-test.ll: -------------------------------------------------------------------------------- 1 | ; RUN: true 2 | ; XFAIL: * 3 | ; XTARGET: darwin 4 | -------------------------------------------------------------------------------- /lib/WatchpointException.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "WatchpointException.h" 3 | 4 | using namespace axe; 5 | 6 | -------------------------------------------------------------------------------- /thirdparty/lit/lit.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | if __name__=='__main__': 4 | import lit 5 | lit.main() 6 | -------------------------------------------------------------------------------- /utils/instgen/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | include_directories(${AXE_SOURCE_DIR}/lib) 2 | 3 | add_executable(instgen InstructionGen.cpp) 4 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/LitFormats.py: -------------------------------------------------------------------------------- 1 | from TestFormats import GoogleTest, ShTest, TclTest 2 | from TestFormats import SyntaxCheckTest, OneCommandPerFileTest 3 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/TclTest/lit.local.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | config.test_format = lit.formats.TclTest() 4 | 5 | config.suffixes = ['.ll'] 6 | -------------------------------------------------------------------------------- /lib/AXEVersion.h.in: -------------------------------------------------------------------------------- 1 | #define AXE_VERSION_MAJOR @AXE_VERSION_MAJOR@ 2 | #define AXE_VERSION_MINOR @AXE_VERSION_MINOR@ 3 | #define AXE_VERSION_TWEAK "@AXE_VERSION_TWEAK@" 4 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/TclTest/tcl-redir-1.ll: -------------------------------------------------------------------------------- 1 | ; RUN: echo 'hi' > %t.1 | echo 'hello' > %t.2 2 | ; RUN: not grep 'hi' %t.1 3 | ; RUN: grep 'hello' %t.2 4 | 5 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/ShExternal/lit.local.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | config.test_format = lit.formats.ShTest(execute_external = True) 4 | 5 | config.suffixes = ['.c'] 6 | 7 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/ShInternal/lit.local.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | config.test_format = lit.formats.ShTest(execute_external = False) 4 | 5 | config.suffixes = ['.c'] 6 | 7 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/required-and-missing.c: -------------------------------------------------------------------------------- 1 | // This test shouldn't be run, the required feature is missing. 2 | // 3 | // RUN: false 4 | // REQUIRES: some-missing-feature-name 5 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/Clang/fsyntax-only.c: -------------------------------------------------------------------------------- 1 | // RUN: clang -fsyntax-only -Xclang -verify %s 2 | 3 | int f0(void) {} // expected-warning {{control reaches end of non-void function}} 4 | 5 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.InTree/test/Bar/dg.exp: -------------------------------------------------------------------------------- 1 | load_lib llvm.exp 2 | 3 | if { [llvm_supports_target X86] } { 4 | RunLLVMTests [lsort [glob -nocomplain $srcdir/$subdir/*.{ll}]] 5 | } 6 | 7 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.OutOfTree/src/test/Foo/dg.exp: -------------------------------------------------------------------------------- 1 | load_lib llvm.exp 2 | 3 | if { [llvm_supports_target X86] } { 4 | RunLLVMTests [lsort [glob -nocomplain $srcdir/$subdir/*.{ll}]] 5 | } 6 | 7 | -------------------------------------------------------------------------------- /test/basic.c: -------------------------------------------------------------------------------- 1 | /* 2 | * RUN: xcc -target=XK-1A %s -o %t1.xe 3 | * RUN: %sim %t1.xe 4 | * RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | * RUN: %sim %t1.xe 6 | */ 7 | 8 | int main() { 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /tools/axe/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | 2 | add_executable(axe-bin 3 | Options.h 4 | Options.cpp 5 | main.cpp) 6 | target_link_libraries(axe-bin axe) 7 | set_target_properties(axe-bin PROPERTIES OUTPUT_NAME axe) 8 | 9 | install(TARGETS axe-bin DESTINATION bin) 10 | -------------------------------------------------------------------------------- /benchmarks/dhry_main.xc: -------------------------------------------------------------------------------- 1 | #ifndef THREADS 2 | #define THREADS 1 3 | #endif 4 | 5 | extern int dhry(); 6 | 7 | int main() 8 | { 9 | #if THREADS == 1 10 | dhry(); 11 | #else 12 | par (int i = 0; i < THREADS; i++) 13 | dhry(); 14 | #endif 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/__init__.py: -------------------------------------------------------------------------------- 1 | """'lit' Testing Tool""" 2 | 3 | from lit import main 4 | 5 | __author__ = 'Daniel Dunbar' 6 | __email__ = 'daniel@zuster.org' 7 | __versioninfo__ = (0, 1, 0) 8 | __version__ = '.'.join(map(str, __versioninfo__)) 9 | 10 | __all__ = [] 11 | -------------------------------------------------------------------------------- /test/Options/max_cycles.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: not %sim %t1.xe --max-cycles 10000 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: not %sim %t1.xe --max-cycles 10000 5 | 6 | int main() { 7 | while (1) {} 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /test/Targets/u_series.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc %s.xn %s -o %t1.xe 2 | // RUN: %sim %t1.xe > %t2.txt 3 | // RUN: cmp %t2.txt %s.expect 4 | 5 | #include 6 | #include 7 | 8 | int main() 9 | { 10 | par { 11 | on tile[0]: printstr("hello\n"); 12 | } 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /test/lit.site.cfg.in: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | # Set some key paths for use by axe test suite config. 4 | config.axe_obj_root = os.path.dirname(os.path.dirname(__file__)) 5 | config.axe_bin_dir = '${CMAKE_BINARY_DIR}/bin' 6 | 7 | # Let the main config do the real work. 8 | lit.load_config(config, '${CMAKE_SOURCE_DIR}/test/lit.cfg') 9 | -------------------------------------------------------------------------------- /utils/genJitGlobalMap/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | find_package(LLVM 3.3 REQUIRED) 2 | 3 | add_executable(genJitGlobalMap genJitGlobalMap.cpp) 4 | 5 | target_link_libraries( 6 | genJitGlobalMap 7 | ${LLVM_LIBRARIES} 8 | ${LLVM_LDFLAGS} 9 | ) 10 | 11 | target_compile_options( 12 | genJitGlobalMap PRIVATE 13 | ${LLVM_CFLAGS} 14 | ) 15 | -------------------------------------------------------------------------------- /test/elf_entry_point.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -nostdlib -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | .text 4 | .align 2 5 | ldc r0, 1 6 | bu fin 7 | .globl _start 8 | _start: 9 | ldc r0, 0 10 | bu fin 11 | 12 | .globl _DoSyscall 13 | _DoSyscall: 14 | retsp 0 15 | 16 | fin: 17 | mov r1, r0 18 | ldc r0, 0 //OSCALL_EXIT 19 | bu _DoSyscall 20 | -------------------------------------------------------------------------------- /test/SystemCalls/is_simulation.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | 6 | .globl main 7 | 8 | .align 2 9 | main: 10 | entsp 1 11 | ldc r0, 99 12 | bl _DoSyscall 13 | eq r0, r0, 1 14 | ecallf r0 15 | ldc r0, 0 16 | retsp 1 17 | -------------------------------------------------------------------------------- /test/helloworld.c: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe > %t2.txt 3 | // RUN: cmp %t2.txt %s.expect 4 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | // RUN: %sim %t1.xe > %t2.txt 6 | // RUN: cmp %t2.txt %s.expect 7 | 8 | #include 9 | 10 | int main() 11 | { 12 | printf("Hello world\n"); 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /lib/NetworkLink.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "NetworkLink.h" 7 | 8 | using namespace axe; 9 | 10 | NetworkLink::~NetworkLink() 11 | { 12 | } 13 | -------------------------------------------------------------------------------- /lib/Peripheral.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Peripheral.h" 7 | 8 | using namespace axe; 9 | 10 | Peripheral::~Peripheral() 11 | { 12 | } 13 | -------------------------------------------------------------------------------- /cmake/Modules/FindLibRt.cmake: -------------------------------------------------------------------------------- 1 | # Locate librt library 2 | # This module defines 3 | # LIBRT_FOUND - System has librt 4 | # LIBRT_LIBRARIES - The librt library 5 | 6 | find_library(LIBRT_LIBRARIES rt) 7 | 8 | include(FindPackageHandleStandardArgs) 9 | # Sets LIBRT_FOUND 10 | find_package_handle_standard_args(LibRt DEFAULT_MSG LIBRT_LIBRARIES) 11 | 12 | mark_as_advanced(LIBRT_LIBRARIES) 13 | -------------------------------------------------------------------------------- /lib/PortInterface.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PortInterface.h" 7 | 8 | using namespace axe; 9 | 10 | PortInterface::~PortInterface() { 11 | 12 | } 13 | -------------------------------------------------------------------------------- /lib/PortSignalTracker.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PortSignalTracker.h" 7 | 8 | using namespace axe; 9 | 10 | PortSignalTracker::PortSignalTracker() : signal(0) {} 11 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.InTree/test/lit.site.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | ## Autogenerated by Makefile ## 4 | # Do not edit! 5 | 6 | # Preserve some key paths for use by main LLVM test suite config. 7 | config.llvm_obj_root = os.path.dirname(os.path.dirname(__file__)) 8 | 9 | # Let the main config do the real work. 10 | lit.load_config(config, os.path.join(config.llvm_obj_root, 'test/lit.cfg')) 11 | -------------------------------------------------------------------------------- /lib/InstructionProperties.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "InstructionProperties.h" 7 | 8 | using namespace axe; 9 | 10 | #define EMIT_INSTRUCTION_PROPERTIES 11 | #include "InstructionGenOutput.inc" 12 | -------------------------------------------------------------------------------- /lib/InstructionTraceInfo.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "InstructionTraceInfo.h" 7 | 8 | using namespace axe; 9 | 10 | #define EMIT_INSTRUCTION_TRACE_INFO 11 | #include "InstructionGenOutput.inc" 12 | -------------------------------------------------------------------------------- /lib/Timeout.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Timeout.h" 7 | #include "SystemState.h" 8 | 9 | using namespace axe; 10 | 11 | void Timeout::run(ticks_t time) 12 | { 13 | throw TimeoutException(time); 14 | } 15 | -------------------------------------------------------------------------------- /test/Instructions/GETSR.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe -mno-dual-issue 4 | // RUN: %sim %t1.xe 5 | 6 | .text 7 | .globl main 8 | 9 | main: 10 | getsr r11, 0xFFFF 11 | eq r11, r11, 0 12 | ecallf r11 13 | 14 | setsr 0x1 15 | setsr 0x2 16 | getsr r11, 0xFFFF 17 | eq r11, r11, 3 18 | ecallf r11 19 | 20 | ldc r0, 0 21 | retsp 0 22 | 23 | -------------------------------------------------------------------------------- /test/Resources/Ports/ignored_output.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | 8 | port p = XS1_PORT_1A; 9 | port q = XS1_PORT_1B; 10 | 11 | int main() 12 | { 13 | for (unsigned i = 0; i < 1000; i++) { 14 | p <: 0; 15 | p <: 1; 16 | } 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /test/SystemCalls/argv_xs2.c: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XCORE-200-EXPLORER -fcmdline-buffer-bytes=512 %s -o %t1.xe 2 | // RUN: %sim --args %t1.xe hello world 3 | #include "string.h" 4 | 5 | int main(int argc, char **argv) { 6 | if (argc != 3) { 7 | return 1; 8 | } 9 | 10 | if (strcmp(argv[1], "hello") != 0) { 11 | return 2; 12 | } 13 | 14 | if (strcmp(argv[2], "world") != 0) { 15 | return 3; 16 | } 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/LLVM.OutOfTree/obj/test/lit.site.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | ## Autogenerated by Makefile ## 4 | # Do not edit! 5 | 6 | # Preserve some key paths for use by main LLVM test suite config. 7 | config.llvm_obj_root = os.path.dirname(os.path.dirname(__file__)) 8 | 9 | # Let the main config do the real work. 10 | lit.load_config(config, os.path.join(config.llvm_obj_root, 11 | '../src/test/lit.cfg')) 12 | -------------------------------------------------------------------------------- /test/Instructions/LDAPB.c: -------------------------------------------------------------------------------- 1 | /* 2 | * RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 3 | * RUN: %sim %t1.xe 4 | */ 5 | #include 6 | 7 | int main(void) { 8 | int x, y; 9 | asm("{ldap r11, main; nop}\n add %0, r11, 0" : "=r" (x)); 10 | asm("{nop; ldap r11, main}\n add %0, r11, 0" : "=r" (y)); 11 | 12 | printf("%08x %08x\n", x, y); 13 | 14 | if (x == y) { 15 | return 0; 16 | } else { 17 | return 1; 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /test/Targets/multicore_l2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XS1-L2A-QF124 %s -o %t1.xe 2 | // RUN: %sim %t1.xe > %t2.txt 3 | // RUN: cmp %t2.txt %s.expect 4 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | // RUN: %sim %t1.xe > %t2.txt 6 | // RUN: cmp %t2.txt %s.expect 7 | 8 | #include 9 | #include 10 | 11 | int main() 12 | { 13 | par { 14 | on stdcore[0]: printstr("hello\n"); 15 | on stdcore[1]: printstr("hello\n"); 16 | } 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /lib/AXEInitialize.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _AXEInitialize_h_ 7 | #define _AXEInitialize_h_ 8 | 9 | namespace axe { 10 | 11 | void AXEInitialize(bool beLazy); 12 | void AXECleanup(); 13 | 14 | } // End namespace axe 15 | 16 | #endif // _AXEInitialize_h_ 17 | -------------------------------------------------------------------------------- /lib/Array.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Array_h_ 7 | #define _Array_h_ 8 | 9 | namespace axe { 10 | 11 | template 12 | constexpr unsigned arraySize(T (&)[size]) { 13 | return size; 14 | } 15 | 16 | }; 17 | 18 | #endif // _Array_h_ 19 | -------------------------------------------------------------------------------- /lib/Peripheral.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Peripheral_h_ 7 | #define _Peripheral_h_ 8 | 9 | namespace axe { 10 | 11 | class Peripheral { 12 | public: 13 | virtual ~Peripheral(); 14 | }; 15 | 16 | } // End axe namespace 17 | 18 | #endif // _Peripheral_h_ 19 | -------------------------------------------------------------------------------- /lib/registerAllPeripherals.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _registerAllPeripherals_h_ 7 | #define _registerAllPeripherals_h_ 8 | 9 | namespace axe { 10 | 11 | void registerAllPeripherals(); 12 | 13 | } // End axe namespace 14 | 15 | #endif //_registerAllPeripherals_h_ 16 | 17 | -------------------------------------------------------------------------------- /lib/Compiler.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Compiler_h_ 7 | #define _Compiler_h_ 8 | 9 | #ifdef __GNUC__ 10 | #define UNUSED(x) x __attribute__((__unused__)) 11 | #endif // __GNUC__ 12 | 13 | #ifndef UNUSED 14 | #define UNUSED(x) x 15 | #endif 16 | 17 | #endif // _Compiler_h_ 18 | -------------------------------------------------------------------------------- /test/Instructions/LDAPF.c: -------------------------------------------------------------------------------- 1 | /* 2 | * RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 3 | * RUN: %sim %t1.xe 4 | */ 5 | #include 6 | 7 | int main(void) { 8 | int x, y; 9 | asm("{ldap r11, somefunc; nop}\n add %0, r11, 0" : "=r" (x)); 10 | asm("{nop; ldap r11, somefunc}\n add %0, r11, 0" : "=r" (y)); 11 | 12 | printf("%08x %08x\n", x, y); 13 | 14 | if (x == y) { 15 | return 0; 16 | } else { 17 | return 1; 18 | } 19 | } 20 | 21 | void somefunc() { 22 | } 23 | -------------------------------------------------------------------------------- /test/Instructions/BLACP.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | 6 | .text 7 | .globl main 8 | 9 | foo: 10 | retsp 0 11 | 12 | bar: 13 | retsp 0 14 | 15 | baz: 16 | retsp 0 17 | 18 | main: 19 | entsp 1 20 | bla cp[1] 21 | bla cp[2] 22 | bla cp[3] 23 | ldc r0, 0 24 | retsp 1 25 | 26 | .section .cp.rodata, "ac", @progbits 27 | .align 4 28 | .word 0 29 | .word foo 30 | .word bar 31 | .word baz 32 | 33 | -------------------------------------------------------------------------------- /test/SystemCalls/overlays.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -foverlay=syscall -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe > %t2.txt 3 | // RUN: cmp %t2.txt %s.expect 4 | // RUN: xcc -foverlay=syscall -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | // RUN: %sim %t1.xe > %t2.txt 6 | // RUN: cmp %t2.txt %s.expect 7 | 8 | #include 9 | 10 | [[overlay]] 11 | void f() { 12 | printstr("f\n"); 13 | } 14 | 15 | [[overlay]] 16 | void g() { 17 | printstr("g\n"); 18 | } 19 | 20 | int main() 21 | { 22 | f(); 23 | g(); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /lib/Timeout.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Timeout_h 7 | #define _Timeout_h 8 | 9 | #include "Runnable.h" 10 | 11 | namespace axe { 12 | 13 | class Timeout : public Runnable { 14 | public: 15 | void run(ticks_t time) override; 16 | }; 17 | 18 | } // End namespace axe 19 | 20 | #endif //_Timeout_h_ 21 | -------------------------------------------------------------------------------- /lib/SDRAM.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2014, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _SDRAM_h_ 7 | #define _SDRAM_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | class PeripheralDescriptor; 14 | 15 | std::unique_ptr getPeripheralDescriptorSDRAM(); 16 | 17 | } // End namespace axe 18 | 19 | #endif // _SDRAM_h_ 20 | -------------------------------------------------------------------------------- /test/Resources/Ports/timestamp.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | 6 | #include 7 | 8 | port p = XS1_PORT_1A; 9 | clock c = XS1_CLKBLK_1; 10 | 11 | int main() { 12 | unsigned time; 13 | set_clock_div(c, 10); 14 | configure_in_port(p, c); 15 | start_clock(c); 16 | for (unsigned i = 0; i < 10; i++) { 17 | p :> void @ time; 18 | if (time != i) 19 | return 1; 20 | } 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /test/Resources/Ports/peek.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | #include 8 | 9 | #define VERIFY(x) do { if (!(x)) _Exit(1); } while(0) 10 | 11 | port p = XS1_PORT_8A; 12 | port q = XS1_PORT_8B; 13 | 14 | int main() { 15 | p <: 0xab; 16 | sync(p); 17 | VERIFY(peek(p) == 0xab); 18 | VERIFY(peek(q) == 0xab); 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /lib/SPIFlash.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _SPIFlash_ 7 | #define _SPIFlash_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | class PeripheralDescriptor; 14 | 15 | std::unique_ptr getPeripheralDescriptorSPIFlash(); 16 | 17 | } // End axe namespace 18 | 19 | #endif // _SPIFlash_ 20 | -------------------------------------------------------------------------------- /lib/UartRx.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | 7 | #ifndef _UartRx_h_ 8 | #define _UartRx_h_ 9 | 10 | #include 11 | 12 | namespace axe { 13 | 14 | class PeripheralDescriptor; 15 | 16 | std::unique_ptr getPeripheralDescriptorUartRx(); 17 | 18 | } // End axe namespace 19 | 20 | #endif // _UartRx_h_ 21 | -------------------------------------------------------------------------------- /test/Resources/ClockBlocks/port_source5.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | 6 | #include 7 | 8 | port p = XS1_PORT_1A; 9 | clock c = XS1_CLKBLK_1; 10 | 11 | int main() 12 | { 13 | timer t; 14 | int time; 15 | t :> time; 16 | configure_in_port(p, c); 17 | par { 18 | p :> void; 19 | { 20 | t when timerafter(time += 100) :> void; 21 | start_clock(c); 22 | } 23 | } 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /lib/JitGlobalMap.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _JitGlobalMap_h_ 7 | #define _JitGlobalMap_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | extern const std::pair jitFunctionMap[]; 14 | extern const unsigned jitFunctionMapSize; 15 | 16 | } 17 | 18 | #endif // _JitGlobalMap_h_ 19 | -------------------------------------------------------------------------------- /lib/LCDScreen.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _LCDScreen_h_ 7 | #define _LCDScreen_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | class PeripheralDescriptor; 14 | 15 | std::unique_ptr getPeripheralDescriptorLCDScreen(); 16 | 17 | } // End namespace axe 18 | 19 | #endif // _LCDScreen_h_ 20 | -------------------------------------------------------------------------------- /lib/PS2Keyboard.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PS2Keyboard_h_ 7 | #define _PS2Keyboard_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | class PeripheralDescriptor; 13 | 14 | std::unique_ptr getPeripheralDescriptorPS2Keyboard(); 15 | } // End namespace axe 16 | 17 | #endif // _PS2Keyboard_h_ 18 | -------------------------------------------------------------------------------- /test/Resources/Ports/outclock.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10200 0x10000 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10200 0x10000 5 | 6 | #include 7 | 8 | out port p = XS1_PORT_1A; 9 | in port q = XS1_PORT_1B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | configure_clock_ref(c, 10); 14 | configure_port_clock_output(p, c); 15 | start_clock(c); 16 | q when pinseq(0) :> void; 17 | q when pinseq(1) :> void; 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: cpp 2 | before_install: 3 | - sudo apt-get update -qq 4 | - sudo apt-get install -qq libboost-dev libelf-dev libxml2-dev libxslt1-dev llvm-3.3-dev 5 | - if [ `uname -m` = x86_64 ]; then sudo apt-get install -qq --force-yes libgd2-xpm ia32-libs ia32-libs-multiarch; fi 6 | - wget http://www.cmake.org/files/v2.8/cmake-2.8.12.2-Linux-i386.sh 7 | - chmod a+x cmake-2.8.12.2-Linux-i386.sh 8 | - sudo ./cmake-2.8.12.2-Linux-i386.sh --skip-license --prefix=/usr/local 9 | compiler: 10 | - clang 11 | script: /usr/local/bin/cmake . && make 12 | dist: precise 13 | -------------------------------------------------------------------------------- /lib/EthernetPhy.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | 7 | #ifndef _EthernetPhy_h_ 8 | #define _EthernetPhy_h_ 9 | 10 | #include 11 | 12 | namespace axe { 13 | 14 | class PeripheralDescriptor; 15 | 16 | std::unique_ptr getPeripheralDescriptorEthernetPhy(); 17 | 18 | } // End axe namespace 19 | 20 | #endif // _EthernetPhy_h_ 21 | -------------------------------------------------------------------------------- /lib/InstructionBitcode.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstructionBitcode_h_ 7 | #define _InstructionBitcode_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | extern const unsigned char instructionBitcode[]; 14 | extern size_t instructionBitcodeSize; 15 | 16 | } // End axe namespace 17 | 18 | #endif //_InstructionBitcode_h_ 19 | -------------------------------------------------------------------------------- /lib/PortHandleClockProxy.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PortHandleClockProxy.h" 7 | #include "Signal.h" 8 | #include "RunnableQueue.h" 9 | 10 | using namespace axe; 11 | 12 | PortHandleClockProxy:: 13 | PortHandleClockProxy(RunnableQueue &s, PortInterface &p) : 14 | PortHandleClockMixin(s), 15 | next(p) 16 | { 17 | } 18 | -------------------------------------------------------------------------------- /lib/NetworkLinkTapDefault.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "NetworkLink.h" 7 | #include 8 | #include 9 | 10 | using namespace axe; 11 | 12 | std::unique_ptr axe::createNetworkLinkTap(const std::string &ifname) 13 | { 14 | std::cerr << "error: network TAP not supported on this platform\n"; 15 | std::exit(1); 16 | } 17 | -------------------------------------------------------------------------------- /lib/PortNames.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortNames_h_ 7 | #define _PortNames_h_ 8 | 9 | #include "Config.h" 10 | #include 11 | 12 | namespace axe { 13 | 14 | bool getPortName(uint32_t id, std::string &name); 15 | bool getPortId(const std::string &name, uint32_t &id); 16 | 17 | } // End axe namespace 18 | 19 | #endif // _PortNames_h_ 20 | -------------------------------------------------------------------------------- /test/Targets/multicore_line.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc %s.xn %s -o %t1.xe 2 | // RUN: %sim %t1.xe > %t2.txt 3 | // RUN: cmp %t2.txt %s.expect 4 | 5 | #include 6 | #include 7 | 8 | int main() 9 | { 10 | par { 11 | on tile[0]: printstr("hello\n"); 12 | on tile[1]: printstr("hello\n"); 13 | on tile[2]: printstr("hello\n"); 14 | on tile[3]: printstr("hello\n"); 15 | on tile[4]: printstr("hello\n"); 16 | on tile[5]: printstr("hello\n"); 17 | on tile[6]: printstr("hello\n"); 18 | on tile[7]: printstr("hello\n"); 19 | } 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests.ObjDir/lit.site.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | # Site specific configuration file. 4 | # 5 | # Typically this will be generated by the build system to automatically set 6 | # certain configuration variables which cannot be autodetected, so that 'lit' 7 | # can easily be used on the command line. 8 | 9 | import os 10 | 11 | # Preserve the obj_root, for use by the main lit.cfg. 12 | config.example_obj_root = os.path.dirname(__file__) 13 | 14 | lit.load_config(config, os.path.join(config.test_source_root, 15 | 'lit.cfg')) 16 | -------------------------------------------------------------------------------- /test/Instructions/BLAT.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | .text 6 | .globl main 7 | .align 2 8 | main: 9 | entsp 1 10 | ldaw r11, cp[table] 11 | ldc r0, 2 12 | blat 1 13 | blat 2 14 | retsp 1 15 | 16 | a: 17 | eq r1, r0, 2 18 | ecallf r0 19 | sub r0, r0, 1 20 | retsp 0 21 | 22 | b: 23 | eq r1, r0, 1 24 | ecallf r0 25 | sub r0, r0, 1 26 | retsp 0 27 | 28 | .section .cp.rodata, "ac", @progbits 29 | .align 4 30 | table: 31 | .word 0 32 | .word a 33 | .word b 34 | -------------------------------------------------------------------------------- /lib/InstructionTraceInfo.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstructionTraceInfo_h_ 7 | #define _InstructionTraceInfo_h_ 8 | 9 | namespace axe { 10 | struct InstructionTraceInfo { 11 | const char *string; 12 | }; 13 | 14 | extern const InstructionTraceInfo instructionTraceInfo[]; 15 | 16 | } // End axe namespace 17 | 18 | #endif //_InstructionTraceInfo_h_ 19 | -------------------------------------------------------------------------------- /test/Options/warn_packet_overtake.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --warn-packet-overtake 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --warn-packet-overtake 5 | #include 6 | 7 | int main() { 8 | chan c; 9 | par { 10 | { 11 | outuchar(c, 1); 12 | outct(c, XS1_CT_END); 13 | outuchar(c, 2); 14 | outct(c, XS1_CT_END); 15 | } 16 | { 17 | inuchar(c); 18 | chkct(c, XS1_CT_END); 19 | inuchar(c); 20 | chkct(c, XS1_CT_END); 21 | } 22 | } 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /lib/TrapInfo.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2014, XMOS Ltd., All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _TrapInfo_h_ 7 | #define _TrapInfo_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | class LoadedElf; 14 | 15 | bool 16 | getDescriptionFromTrapInfoSection(const LoadedElf *loadedElf, uint32_t spc, 17 | std::string &desc); 18 | 19 | } // End axe namespace 20 | 21 | #endif // _TrapInfo_h_ 22 | -------------------------------------------------------------------------------- /lib/PortAliases.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PortAliases.h" 7 | 8 | using namespace axe; 9 | 10 | bool PortAliases:: 11 | lookup(const std::string &name, std::string &core, std::string &port) const 12 | { 13 | auto it = aliases.find(name); 14 | if (it == aliases.end()) 15 | return false; 16 | core = it->second.first; 17 | port = it->second.second; 18 | return true; 19 | } 20 | -------------------------------------------------------------------------------- /lib/XNTransform.xslt: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /thirdparty/lit/TODO: -------------------------------------------------------------------------------- 1 | - Move temp directory name into local test config. 2 | 3 | - Add --show-unsupported, don't show by default? 4 | 5 | - Finish documentation. 6 | 7 | - Optionally use multiprocessing. 8 | 9 | - Support llvmc and ocaml tests. 10 | 11 | - Support valgrind in all configs, and LLVM style valgrind. 12 | 13 | - Provide test suite config for running unit tests. 14 | 15 | - Support a timeout / ulimit. 16 | 17 | - Support "disabling" tests? The advantage of making this distinct from XFAIL 18 | is it makes it more obvious that it is a temporary measure (and lit can put 19 | in a separate category). 20 | -------------------------------------------------------------------------------- /lib/InstructionBitcode.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "InstructionBitcode.h" 7 | 8 | using namespace axe; 9 | 10 | const unsigned char axe::instructionBitcode[] = { 11 | #include "InstructionBitcode.inc" 12 | , 0x00 // Ensure null termination. 13 | }; 14 | 15 | /// Size of LLVMModule excluding the terminating null byte. 16 | size_t axe::instructionBitcodeSize = sizeof(instructionBitcode) - 1; 17 | -------------------------------------------------------------------------------- /test/Options/multi_loopback.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback PORT_8A PORT_8B --loopback PORT_8A PORT_8C 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback PORT_8A PORT_8B --loopback PORT_8A PORT_8C 5 | 6 | #include 7 | #include 8 | 9 | port p1 = XS1_PORT_8A; 10 | port p2 = XS1_PORT_8B; 11 | port p3 = XS1_PORT_8C; 12 | 13 | int main() 14 | { 15 | int x, y; 16 | p1 <: 0x5e; 17 | sync(p1); 18 | p2 :> x; 19 | p3 :> y; 20 | if (x != 0x5e) 21 | _Exit(1); 22 | if (y != 0x5e) 23 | _Exit(1); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /lib/Register.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Register.h" 7 | 8 | const char *axe::registerNames[] = { 9 | "r0", 10 | "r1", 11 | "r2", 12 | "r3", 13 | "r4", 14 | "r5", 15 | "r6", 16 | "r7", 17 | "r8", 18 | "r9", 19 | "r10", 20 | "r11", 21 | "cp", 22 | "dp", 23 | "sp", 24 | "lr", 25 | "et", 26 | "ed", 27 | "kep", 28 | "ksp", 29 | "spc", 30 | "sed", 31 | "ssr" 32 | }; 33 | -------------------------------------------------------------------------------- /test/SelfModiyingCode/basic.S: -------------------------------------------------------------------------------- 1 | /* 2 | * RUN: xcc -target=XK-1A %s -o %t1.xe 3 | * RUN: %sim %t1.xe 4 | * RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | * RUN: %sim %t1.xe 6 | */ 7 | 8 | .section .dp.data, "awd", @progbits 9 | .align 4 10 | ldc1: 11 | ldc r0, 1 12 | 13 | .text 14 | .globl main 15 | .align 2 16 | f: 17 | nop 18 | patch_address: 19 | ldc r0, 0 20 | bt r0, end 21 | ldaw r11, dp[ldc1] 22 | ld16s r1, r11[r0] 23 | ldap r11, patch_address 24 | st16 r1, r11[r0] 25 | end: 26 | retsp 0 27 | 28 | main: 29 | entsp 1 30 | bl f 31 | ecallt r0 32 | bl f 33 | eq r0, r0, 1 34 | ecallf r0 35 | ldc r0, 0 36 | retsp 1 37 | -------------------------------------------------------------------------------- /cmake/Modules/FindClang.cmake: -------------------------------------------------------------------------------- 1 | # Locate Clang 2 | # This module defines 3 | # CLANG_FOUND - System has LLVM 4 | # CLANG_EXECUTABLE - The clang executable 5 | # CLANGPLUSPLUS_EXECUTABLE - The clang++ executable 6 | 7 | find_program( 8 | CLANG_EXECUTABLE NAMES clang 9 | DOC "clang executable") 10 | 11 | find_program( 12 | CLANGPLUSPLUS_EXECUTABLE NAMES clang++ 13 | DOC "clang++ executable") 14 | 15 | include(FindPackageHandleStandardArgs) 16 | # Sets CLANG_FOUND 17 | find_package_handle_standard_args( 18 | Clang DEFAULT_MSG CLANG_EXECUTABLE CLANGPLUSPLUS_EXECUTABLE) 19 | 20 | mark_as_advanced(CLANG_EXECUTABLE) 21 | mark_as_advanced(CLANGPLUSPLUS_EXECUTABLE) 22 | -------------------------------------------------------------------------------- /test/Instructions/BLA.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | .text 4 | foo: 5 | .issue_mode dual 6 | dualentsp 1 7 | 8 | // Load the link register into r0 9 | ldaw r2, sp[0] 10 | add r1, r2, 4 11 | set sp, r1 12 | ldw r0, sp[0] 13 | set sp, r2 14 | 15 | // Check the first bit of the link register is set 16 | mkmsk r1, 1 17 | and r0, r0, r1 18 | bf r0, return_false 19 | ldc r0, 0 20 | retsp 1 21 | return_false: 22 | ldc r0, 1 23 | retsp 1 24 | 25 | .globl main 26 | main: 27 | .issue_mode dual 28 | DUALENTSP_lu6 1 29 | ldap r11, foo 30 | bla r11 31 | retsp 1 32 | -------------------------------------------------------------------------------- /test/Resources/Ports/timed2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | #include 8 | 9 | out port TXD = XS1_PORT_1A; 10 | in port RXD = XS1_PORT_1B; 11 | 12 | int main() 13 | { 14 | unsigned start; 15 | TXD <: 0 @ start; 16 | TXD @ start + 100 <: 1; 17 | par { 18 | { 19 | TXD @ start + 200 <: 1; 20 | } 21 | { 22 | unsigned x; 23 | RXD @ start + 150 :> x; 24 | if (x != 1) 25 | exit(1); 26 | } 27 | } 28 | return 0; 29 | } 30 | -------------------------------------------------------------------------------- /test/Resources/Ports/timed.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback PORT_1A PORT_1B 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback PORT_1A PORT_1B 5 | 6 | #include 7 | 8 | port p = XS1_PORT_1A; 9 | port q = XS1_PORT_1B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned time; 14 | int x; 15 | configure_in_port(p, c); 16 | configure_out_port(q, c, 0); 17 | configure_clock_ref(c, 10); 18 | start_clock(c); 19 | q @ 10 <: 1; 20 | p @ 9 :> x; 21 | if (x != 0) 22 | return 1; 23 | p @ 10 :> x; 24 | if (x != 1) 25 | return 2; 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /test/Resources/paused_on.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: not axe %t1.xe > %t2.txt 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: not axe %t1.xe > %t2.txt 5 | 6 | #include 7 | 8 | unsigned alloc_lock() 9 | { 10 | unsigned lock; 11 | asm("getr %0, 5" : "=r"(lock)); 12 | return lock; 13 | } 14 | 15 | void acquire_lock(unsigned lock) 16 | { 17 | asm("in %0, res[%0]" : : "r"(lock)); 18 | } 19 | 20 | int x; 21 | 22 | int main() 23 | { 24 | chan c; 25 | unsigned lock = alloc_lock(); 26 | acquire_lock(lock); 27 | par { 28 | c :> int; 29 | acquire_lock(lock); 30 | x = 1; 31 | } 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /lib/PeripheralNode.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PeripheralNode_h 7 | #define _PeripheralNode_h 8 | 9 | #include "Node.h" 10 | 11 | namespace axe { 12 | 13 | class PeripheralNode : public Node { 14 | public: 15 | PeripheralNode(); 16 | void finalize() override; 17 | ChanEndpoint *getOutgoingChanendDest(ResourceID ID) override; 18 | ChanEndpoint *getLocalChanendDest(ResourceID ID) override; 19 | }; 20 | 21 | } // End axe namespace 22 | 23 | #endif // _PeripheralNode_h 24 | -------------------------------------------------------------------------------- /lib/Runnable.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Runnable_h_ 7 | #define _Runnable_h_ 8 | 9 | #include "Config.h" 10 | #include 11 | 12 | namespace axe { 13 | 14 | class Runnable { 15 | protected: 16 | ~Runnable() = default; 17 | public: 18 | Runnable *prev; 19 | Runnable *next; 20 | ticks_t wakeUpTime; 21 | 22 | virtual void run(ticks_t time) = 0; 23 | Runnable() : prev(0), next(0) {} 24 | }; 25 | 26 | } // End axe namespace 27 | 28 | #endif // _Runnable_h_ 29 | -------------------------------------------------------------------------------- /test/Resources/Ports/buffered.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | 8 | out port p = XS1_PORT_8A; 9 | buffered in port:32 q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned time; 14 | int val; 15 | configure_in_port(q, c); 16 | configure_out_port(p, c, 0); 17 | configure_clock_ref(c, 10); 18 | start_clock(c); 19 | p @ 10 <: 0x28; 20 | p <: 0x2c; 21 | p <: 0x54; 22 | p <: 0x99; 23 | 24 | q @ 13 :> val; 25 | if (val != 0x99542c28) 26 | return 1; 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /test/Resources/Ports/timing2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | 6 | out port p = XS1_PORT_1A; 7 | clock c = XS1_CLKBLK_1; 8 | 9 | #define EXPECTED ((100 * 100 * 8) / 100) 10 | #define TOLERANCE 5 11 | 12 | int main() { 13 | timer t; 14 | unsigned t1, t2; 15 | unsigned diff; 16 | configure_clock_rate(c, 100, 8); //12.5MHz 17 | configure_out_port(p, c, 0); 18 | start_clock(c); 19 | p <: 0; 20 | p <: 0; 21 | t :> t1; 22 | for (unsigned i = 0; i < 100; i++) { 23 | p <: 0; 24 | } 25 | t :> t2; 26 | diff = t2 - t1; 27 | if (diff < EXPECTED - TOLERANCE || 28 | diff > EXPECTED + TOLERANCE) 29 | return 1; 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /test/Exceptions/ecall.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s %exception_expect -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s %exception_expect -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .text 8 | .globl main 9 | .align 2 10 | main: 11 | entsp 3 12 | stw r4, sp[1] 13 | stw r5, sp[2] 14 | ldc r4, 0 15 | ldc r5, 1 16 | 17 | // ecallt 18 | ecallt r4 19 | ldc r0, 8 20 | ldc r1, 0 21 | bl exception_expect 22 | ecallt r5 23 | bl exception_check 24 | 25 | // ecallf 26 | ecallf r5 27 | ldc r0, 8 28 | ldc r1, 0 29 | bl exception_expect 30 | ecallf r4 31 | bl exception_check 32 | 33 | ldw r4, sp[1] 34 | ldw r5, sp[2] 35 | ldc r0, 0 36 | retsp 3 37 | -------------------------------------------------------------------------------- /test/Instructions/xor4.c: -------------------------------------------------------------------------------- 1 | /* 2 | * RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 3 | * RUN: %sim %t1.xe 4 | */ 5 | #include 6 | #include 7 | #include 8 | #define VERIFY(x) do { if(!(x)) { _Exit(1); }} while(0) 9 | 10 | static inline uint32_t xor4(uint32_t a, uint32_t b, uint32_t c, uint32_t d) 11 | { 12 | uint32_t result; 13 | asm("xor4 %0, %1, %2, %3, %4" : 14 | "=r"(result) : 15 | "r"(a), "r"(b), "r"(c), "r"(d)); 16 | return result; 17 | } 18 | 19 | int main() { 20 | VERIFY(xor4(2, 4, 8, 16) == 30); 21 | VERIFY(xor4(1, 4, 16, 64) == 85); 22 | VERIFY(xor4(2, 4, 2, 4) == 0); 23 | VERIFY(xor4(0xffffffff, 0xffff0000, 0xff00, 0) == 255); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /test/Resources/Ports/buffered2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | 8 | buffered out port:32 p = XS1_PORT_8A; 9 | in port q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned time; 14 | int val; 15 | configure_in_port(q, c); 16 | configure_out_port(p, c, 0); 17 | configure_clock_ref(c, 10); 18 | start_clock(c); 19 | p @ 10 <: 0x99542c28; 20 | q @10 :>>> val; 21 | q :>>> val; 22 | q :>>> val; 23 | q :>>> val; 24 | if (val != 0x99542c28) 25 | return 1; 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /lib/InstFunction.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstFunction_h_ 7 | #define _InstFunction_h_ 8 | 9 | namespace axe { 10 | 11 | class Thread; 12 | 13 | enum class InstReturn { 14 | /// Continue the current trace. 15 | CONTINUE, 16 | /// End the current trace. 17 | END_TRACE, 18 | /// End execution of the current thread. 19 | END_THREAD_EXECUTION, 20 | }; 21 | 22 | typedef InstReturn (*InstFunction_t)(Thread &); 23 | 24 | } // End axe namespace 25 | 26 | #endif // _InstFunction_h_ 27 | -------------------------------------------------------------------------------- /test/Resources/Ports/timing.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | 6 | in port p = XS1_PORT_1A; 7 | clock c = XS1_CLKBLK_1; 8 | 9 | #define ITERATIONS 100 10 | #define EXPECTED ((ITERATIONS * 100 * 8) / 100) 11 | #define TOLERANCE 5 12 | 13 | int main() { 14 | timer t; 15 | unsigned t1, t2; 16 | unsigned diff; 17 | configure_clock_rate(c, 100, 8); //12.5MHz 18 | configure_in_port(p, c); 19 | start_clock(c); 20 | p :> void; 21 | t :> t1; 22 | for (unsigned i = 0; i < ITERATIONS; i++) { 23 | p :> void; 24 | } 25 | t :> t2; 26 | diff = t2 - t1; 27 | if (diff < EXPECTED - TOLERANCE || 28 | diff > EXPECTED + TOLERANCE) 29 | return 1; 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /test/Resources/Threads/unsynchronised.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .globl main 8 | .text 9 | .align 2 10 | main: 11 | getr r0, XS1_RES_TYPE_THREAD 12 | getr r1, XS1_RES_TYPE_CHANEND 13 | getr r2, XS1_RES_TYPE_CHANEND 14 | setd res[r2], r1 15 | ldap r11, thread 16 | init t[r0]:pc, r11 17 | ldap r11, kill_thread 18 | init t[r0]:lr, r11 19 | set t[r0]:r0, r2 20 | start t[r0] 21 | chkct res[r1], XS1_CT_END 22 | freer res[r1] 23 | freer res[r2] 24 | ldc r0, 0 25 | retsp 0 26 | 27 | .align 2 28 | kill_thread: 29 | freet 30 | 31 | .align 2 32 | thread: 33 | outct res[r0], XS1_CT_END 34 | retsp 0 35 | -------------------------------------------------------------------------------- /lib/PortSignalTracker.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortSignalTracker_h_ 7 | #define _PortSignalTracker_h_ 8 | 9 | #include "PortInterface.h" 10 | #include "Signal.h" 11 | 12 | namespace axe { 13 | 14 | class PortSignalTracker : public PortInterface { 15 | Signal signal; 16 | public: 17 | PortSignalTracker(); 18 | void seePinsChange(const Signal &s, ticks_t time) override { signal = s; } 19 | const Signal &getSignal() const { return signal; } 20 | }; 21 | 22 | } // End axe namespace 23 | 24 | #endif //_PortSignalTracker_h_ 25 | -------------------------------------------------------------------------------- /lib/JitGlobalMap.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "JitGlobalMap.h" 7 | #include "Array.h" 8 | 9 | using namespace axe; 10 | 11 | #define DO_FUNCTION(name) extern "C" void name(); 12 | #include "JitGlobalMap.inc" 13 | #undef DO_FUNCTION 14 | 15 | #define QUOTE_AUX(x) #x 16 | #define QUOTE(x) QUOTE_AUX(x) 17 | const std::pair axe::jitFunctionMap[] = { 18 | #define DO_FUNCTION(name) { QUOTE(name), &name }, 19 | #include "JitGlobalMap.inc" 20 | }; 21 | 22 | const unsigned axe::jitFunctionMapSize = arraySize(jitFunctionMap); 23 | -------------------------------------------------------------------------------- /lib/WatchpointException.h: -------------------------------------------------------------------------------- 1 | #ifndef __WatchpointException_ 2 | #define __WatchpointException_ 3 | 4 | #include 5 | #include "Resource.h" 6 | #include "WatchpointManager.h" 7 | 8 | namespace axe { 9 | 10 | class Thread; 11 | class WatchpointException { 12 | private: 13 | uint32_t address; 14 | public: 15 | WatchpointType type; 16 | Thread &thread; 17 | ticks_t time; 18 | WatchpointException(WatchpointType t, uint32_t addr, Thread &thrd, 19 | ticks_t tm) : 20 | address(addr), type(t), thread(thrd), time(tm) {} 21 | uint32_t getAddr() { return address; } 22 | ticks_t getTime() const { return time; } 23 | Thread &getThread() const { return thread; } 24 | }; 25 | 26 | } // End axe namespace 27 | 28 | #endif // __WatchpointException_ 29 | -------------------------------------------------------------------------------- /lib/XEReader.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _XEReader_h 7 | #define _XEReader_h 8 | 9 | #include "Tracer.h" 10 | #include 11 | 12 | namespace axe { 13 | 14 | class XE; 15 | class SystemState; 16 | class PortAliases; 17 | 18 | class XEReader { 19 | XE &xe; 20 | public: 21 | XEReader(XE &x) : xe(x) {} 22 | std::unique_ptr 23 | readConfig(std::unique_ptr tracer = std::unique_ptr()); 24 | void readPortAliases(PortAliases &aliases); 25 | }; 26 | 27 | } // End axe namespace 28 | 29 | #endif // _XEReader_h 30 | -------------------------------------------------------------------------------- /test/Resources/Ports/partial_output.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | 8 | buffered out port:32 p = XS1_PORT_8A; 9 | buffered in port:32 q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned time; 14 | int val; 15 | configure_in_port(q, c); 16 | configure_out_port(p, c, 0); 17 | configure_clock_ref(c, 10); 18 | start_clock(c); 19 | partout_timed(p, 8, 0x28, 10); 20 | partout(p, 8, 0x2c); 21 | partout(p, 8, 0x54); 22 | partout(p, 8, 0x99); 23 | 24 | q @ 13 :> val; 25 | if (val != 0x99542c28) 26 | return 1; 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /lib/XMLUtils.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _XMLUtils_h_ 7 | #define _XMLUtils_h_ 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | xmlNode *findChild(xmlNode *node, const char *name); 15 | xmlAttr *findAttribute(xmlNode *node, const char *name); 16 | xmlDoc *applyXSLTTransform(xmlDoc *doc, const char *transformData); 17 | bool checkDocAgainstSchema(xmlDoc *doc, const char *schemaData, 18 | size_t schemaSize); 19 | 20 | } // End axe namespace 21 | 22 | #endif // _XMLUtils_h_ 23 | -------------------------------------------------------------------------------- /test/Resources/Ports/readyOut.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | 8 | out buffered port:32 p = XS1_PORT_1C; 9 | port readyOut = XS1_PORT_1A; 10 | in buffered port:32 loopback = XS1_PORT_1B; 11 | clock clk = XS1_CLKBLK_1; 12 | 13 | int main() 14 | { 15 | unsigned x; 16 | configure_clock_rate(clk, 100, 6); 17 | configure_out_port_strobed_master(p, readyOut, clk, 0); 18 | configure_in_port(loopback, clk); 19 | p @ 5 <: 0; 20 | start_clock(clk); 21 | loopback :> x; 22 | if (x != 0xffffffe0) 23 | return 1; 24 | loopback :> x; 25 | if (x != 0x1f) 26 | return 2; 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /lib/Exceptions.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Exceptions_h_ 7 | #define _Exceptions_h_ 8 | 9 | namespace axe { 10 | 11 | enum ExceptionType { 12 | ET_LINK_ERROR = 1, 13 | ET_ILLEGAL_PC = 2, 14 | ET_ILLEGAL_INSTRUCTION = 3, 15 | ET_ILLEGAL_RESOURCE = 4, 16 | ET_LOAD_STORE = 5, 17 | ET_ILLEGAL_PS = 6, 18 | ET_ARITHMETIC = 7, 19 | ET_ECALL = 8, 20 | ET_RESOURCE_DEP = 9, 21 | ET_KCALL = 15 22 | }; 23 | 24 | class Exceptions { 25 | public: 26 | static const char *getExceptionName(int type); 27 | }; 28 | 29 | } // End axe namespace 30 | 31 | #endif // _Exceptions_h_ 32 | -------------------------------------------------------------------------------- /test/Resources/Ports/partial_input_timed.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | 8 | buffered out port:32 p = XS1_PORT_8A; 9 | buffered in port:32 q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned tmp; 14 | configure_in_port(q, c); 15 | configure_out_port(p, c, 0); 16 | configure_clock_ref(c, 10); 17 | start_clock(c); 18 | p @ 10 <: 0x99542c28; 19 | set_port_shift_count(q, 24); 20 | q @ 10 :> tmp; 21 | if ((tmp >> 24) != 0x28) 22 | return 1; 23 | set_port_shift_count(q, 8); 24 | q @ 12 :> tmp; 25 | if ((tmp >> 24) != 0x54) 26 | return 2; 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /lib/LoadedElf.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2014, XMOS Ltd., All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _LoadedElf_h_ 7 | #define _LoadedElf_h_ 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | class XEElfSector; 15 | 16 | class LoadedElf { 17 | char *buf; 18 | Elf *elf; 19 | public: 20 | LoadedElf(const XEElfSector *elfSector); 21 | LoadedElf(const LoadedElf &) = delete; 22 | LoadedElf &operator=(const LoadedElf &) = delete; 23 | ~LoadedElf(); 24 | Elf *getElf() const { return elf; } 25 | const char *getBuf() const { return buf; } 26 | }; 27 | 28 | } // End axe namespace 29 | 30 | #endif // _LoadedElf_h_ 31 | -------------------------------------------------------------------------------- /test/SystemCalls/io.c: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | 6 | #include 7 | int main(void) { 8 | char* filename = "temp_axe_io_test.txt"; 9 | char string[] = "abcdefghijklmnopqrstuvwxyz"; // "\0" 10 | FILE *fp = fopen(filename, "w+"); 11 | if (!fp) return 1; 12 | if (fwrite(string, 1, sizeof(string),fp) != sizeof(string)) return 1; 13 | if (fseek(fp, -17, SEEK_CUR) != 0) return 1; 14 | if (fgetc(fp) != 'k') return 1; 15 | if (fseek(fp, 0, SEEK_SET) != 0) return 1; 16 | if (fgetc(fp) != 'a') return 1; 17 | if (fseek(fp, -2, SEEK_END) != 0) return 1; 18 | if (fgetc(fp) != 'z') return 1; 19 | if (fclose(fp) != 0) return 1; 20 | if (remove(filename) != 0) return 1; 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /lib/LLVMExtra.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _LLVMExtra_h_ 7 | #define _LLVMExtra_h_ 8 | 9 | #include "llvm-c/Core.h" 10 | #include "llvm-c/ExecutionEngine.h" 11 | 12 | #ifdef __cplusplus 13 | extern "C" { 14 | #endif 15 | 16 | LLVMBool LLVMExtraInlineFunction(LLVMValueRef call); 17 | 18 | void LLVMExtraRegisterJitDisassembler(LLVMExecutionEngineRef EE, 19 | const char *triple); 20 | 21 | void LLVMDisableSymbolSearching(LLVMExecutionEngineRef EE, LLVMBool Disable); 22 | 23 | #ifdef __cplusplus 24 | } // extern "C" 25 | #endif 26 | 27 | #endif //_LLVMExtra_h_ 28 | -------------------------------------------------------------------------------- /test/SystemCalls/files.c: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe -DFILENAME=\"%t2\" 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe -DFILENAME=\"%t2\" 4 | // RUN: %sim %t1.xe 5 | 6 | #include 7 | #include 8 | 9 | #ifndef FILENAME 10 | #error "Must define FILENAME" 11 | #endif 12 | 13 | int main() 14 | { 15 | char buf[4]; 16 | int fd = _open(FILENAME, O_CREAT | O_WRONLY, 0644); 17 | if (fd < 0) 18 | return 1; 19 | if (_write(fd, "foo", 4) != 4) 20 | return 1; 21 | if (_close(fd) < 0) 22 | return 1; 23 | 24 | fd = _open(FILENAME, O_RDONLY, 0); 25 | if (fd < 0) 26 | return 1; 27 | if (_read(fd, buf, 4) != 4) 28 | return 1; 29 | if (memcmp(buf, "foo", 4) != 0) 30 | return 1; 31 | if (_close(fd) < 0) 32 | return 1; 33 | 34 | return 0; 35 | } 36 | -------------------------------------------------------------------------------- /lib/NetworkLink.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _NetworkLink_h 7 | #define _NetworkLink_h 8 | 9 | #include 10 | #include 11 | #include 12 | 13 | namespace axe { 14 | 15 | class NetworkLink { 16 | public: 17 | static const unsigned maxFrameSize = 1500 + 18; 18 | virtual ~NetworkLink(); 19 | virtual void transmitFrame(const uint8_t *data, unsigned size) = 0; 20 | virtual bool receiveFrame(uint8_t *data, unsigned &size) = 0; 21 | }; 22 | 23 | std::unique_ptr createNetworkLinkTap(const std::string &ifname); 24 | 25 | } // End axe namespace 26 | 27 | #endif // _NetworkLink_h 28 | -------------------------------------------------------------------------------- /lib/PortHandleClockProxy.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortHandleClockProxy_h_ 7 | #define _PortHandleClockProxy_h_ 8 | 9 | #include "Signal.h" 10 | #include "PortHandleClockMixin.h" 11 | 12 | namespace axe { 13 | 14 | class PortHandleClockProxy : public PortHandleClockMixin { 15 | PortInterface &next; 16 | public: 17 | PortHandleClockProxy(RunnableQueue &scheduler, PortInterface &next); 18 | void seePinsValueChange(uint32_t value, ticks_t time) { 19 | next.seePinsChange(Signal(value), time); 20 | } 21 | }; 22 | 23 | } // End axe namespace 24 | 25 | #endif // _PortHandleClockProxy_h_ 26 | -------------------------------------------------------------------------------- /test/Resources/Ports/readyIn.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | 8 | port loopback = XS1_PORT_1B; 9 | port readyIn = XS1_PORT_1A; 10 | in buffered port:32 p = XS1_PORT_1C; 11 | clock clk = XS1_CLKBLK_1; 12 | 13 | int main() 14 | { 15 | timer t; 16 | unsigned x; 17 | unsigned time; 18 | configure_clock_rate(clk, 100, 6); 19 | configure_in_port_strobed_slave(p, readyIn, clk); 20 | configure_out_port(loopback, clk, 0); 21 | start_clock(clk); 22 | t :> time; 23 | select { 24 | case t when timerafter(time + 200) :> void: 25 | break; 26 | case p :> void: 27 | return 1; 28 | } 29 | loopback <: 1; 30 | p :> void; 31 | return 0; 32 | } 33 | -------------------------------------------------------------------------------- /lib/WatchpointManager.cpp: -------------------------------------------------------------------------------- 1 | #include "WatchpointManager.h" 2 | #include "Tracer.h" 3 | #include 4 | 5 | using namespace axe; 6 | 7 | void WatchpointManager::setWatchpoint(WatchpointType type, uint32_t lowAddr, uint32_t highAddr) 8 | { 9 | Watchpoint w = Watchpoint(type, lowAddr, highAddr); 10 | watchpoints.insert(w); 11 | } 12 | 13 | void WatchpointManager::unsetWatchpoint(WatchpointType type, uint32_t lowAddr, uint32_t highAddr) 14 | { 15 | watchpoints.erase(Watchpoint(type, lowAddr, highAddr)); 16 | } 17 | 18 | bool WatchpointManager::isWatchpointAddress(WatchpointType t, uint32_t address, uint8_t ldst_size) 19 | { 20 | for (const Watchpoint &watchpoint : watchpoints) { 21 | if (t == watchpoint.type && 22 | (address + ldst_size > watchpoint.begin && address <= watchpoint.end)) 23 | return true; 24 | } 25 | return false; 26 | } 27 | -------------------------------------------------------------------------------- /test/Resources/Chanends/pause.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .text 8 | .align 2 9 | .globl main 10 | main: 11 | getr r0, XS1_RES_TYPE_CHANEND 12 | getr r1, XS1_RES_TYPE_CHANEND 13 | getr r2, XS1_RES_TYPE_CHANEND 14 | setd res[r1], r0 15 | setd res[r2], r0 16 | 17 | out res[r1], r1 18 | outct res[r1], XS1_CT_PAUSE 19 | 20 | in r3, res[r0] 21 | eq r3, r3, r1 22 | ecallf r3 23 | 24 | out res[r2], r2 25 | outct res[r2], XS1_CT_END 26 | 27 | in r3, res[r0] 28 | chkct res[r0], XS1_CT_END 29 | eq r3, r3, r2 30 | ecallf r3 31 | 32 | outct res[r1], XS1_CT_END 33 | chkct res[r0], XS1_CT_END 34 | 35 | freer res[r0] 36 | freer res[r1] 37 | freer res[r2] 38 | 39 | ldc r0, 0 40 | retsp 0 41 | -------------------------------------------------------------------------------- /test/Resources/Ports/partial_input.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | 8 | buffered out port:32 p = XS1_PORT_8A; 9 | buffered in port:32 q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned time; 14 | int val; 15 | int tmp; 16 | configure_in_port(q, c); 17 | configure_out_port(p, c, 0); 18 | configure_clock_ref(c, 10); 19 | start_clock(c); 20 | p @ 10 <: 0x99542c28; 21 | q @ 10 :> val; 22 | val >>= 24; 23 | tmp = partin(q, 8); 24 | val |= tmp << 8; 25 | tmp = partin(q, 8); 26 | val |= tmp << 16; 27 | tmp = partin(q, 8); 28 | val |= tmp << 24; 29 | if (val != 0x99542c28) 30 | return 1; 31 | return 0; 32 | } 33 | -------------------------------------------------------------------------------- /lib/Range.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Range_h_ 7 | #define _Range_h_ 8 | 9 | namespace axe { 10 | 11 | template class range { 12 | T beginIt; 13 | T endIt; 14 | public: 15 | range(T b, T e) : beginIt(b), endIt(e) {} 16 | 17 | T begin() { return beginIt; } 18 | T end() { return endIt; } 19 | }; 20 | 21 | template range make_range(T begin, T end) { 22 | return range(begin, end); 23 | } 24 | 25 | template range make_range(const std::pair &p) { 26 | return range(p.first, p.second); 27 | } 28 | } // End namespace axe 29 | 30 | #endif // _Range_h_ 31 | -------------------------------------------------------------------------------- /test/Resources/Ports/readyOut2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | #include 8 | 9 | in buffered port:32 p = XS1_PORT_1C; 10 | port readyOut = XS1_PORT_1A; 11 | in buffered port:32 loopback = XS1_PORT_1B; 12 | clock clk = XS1_CLKBLK_1; 13 | 14 | int main() 15 | { 16 | unsigned x; 17 | configure_clock_rate(clk, 100, 6); 18 | configure_in_port_strobed_master(p, readyOut, clk); 19 | configure_in_port(loopback, clk); 20 | start_clock(clk); 21 | loopback :> x; 22 | if (x != 0xfffffffe) 23 | _Exit(1); 24 | loopback :> x; 25 | if (x != 0xffffffff) 26 | _Exit(2); 27 | loopback :> x; 28 | if (x != 0x00000001) 29 | _Exit(3); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /lib/BreakpointManager.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _BreakpointManager_h 7 | #define _BreakpointManager_h 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | class Core; 15 | 16 | enum class BreakpointType { 17 | Exception, 18 | Syscall, 19 | Other 20 | }; 21 | 22 | class BreakpointManager { 23 | std::map,BreakpointType> breakpointInfo; 24 | public: 25 | bool setBreakpoint(Core &c, uint32_t address, BreakpointType type); 26 | BreakpointType getBreakpointType(Core &c, uint32_t address); 27 | void unsetBreakpoints(); 28 | }; 29 | 30 | } 31 | 32 | #endif // _BreakpointManager_h 33 | -------------------------------------------------------------------------------- /lib/PortAliases.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortAliases_h_ 7 | #define _PortAliases_h_ 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | class PortAliases { 15 | std::map> aliases; 16 | public: 17 | void add(const std::string &name, const std::string &core, 18 | const std::string &port) { 19 | aliases.insert(std::make_pair(name, std::make_pair(core, port))); 20 | } 21 | bool lookup(const std::string &name, std::string &core, 22 | std::string &port) const; 23 | }; 24 | 25 | } // End axe namespace 26 | 27 | #endif // _PortAliases_h_ 28 | -------------------------------------------------------------------------------- /test/Resources/Ports/timed_direction_change.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback XS1_PORT_16A XS1_PORT_16B 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback XS1_PORT_16A XS1_PORT_16B 5 | 6 | #include 7 | #include 8 | 9 | port p = XS1_PORT_16A; 10 | port q = XS1_PORT_16B; 11 | clock clk = XS1_CLKBLK_1; 12 | 13 | int main() 14 | { 15 | int x; 16 | configure_in_port(q, clk); 17 | configure_out_port(p, clk, 0x1234); 18 | configure_clock_ref(clk, 10); 19 | start_clock(clk); 20 | par { 21 | { 22 | start_clock(clk); 23 | p @ 100 :> void; 24 | } 25 | { 26 | int x, y; 27 | q @ 99 :> x; 28 | q :> y; 29 | if (x != 0x1234) 30 | _Exit(1); 31 | if (y != 0) 32 | _Exit(1); 33 | } 34 | } 35 | return 0; 36 | } 37 | -------------------------------------------------------------------------------- /lib/PeripheralRegistry.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PeripheralRegistry_h 7 | #define _PeripheralRegistry_h 8 | 9 | #include 10 | #include 11 | #include 12 | #include "AccessSecondIterator.h" 13 | 14 | namespace axe { 15 | 16 | class PeripheralDescriptor; 17 | 18 | namespace PeripheralRegistry { 19 | typedef AccessSecondIterator::iterator> iterator; 20 | void add(std::unique_ptr p); 21 | PeripheralDescriptor *get(const std::string &s); 22 | iterator begin(); 23 | iterator end(); 24 | }; 25 | 26 | } // End axe namespace 27 | 28 | #endif // _PeripheralRegistry_h 29 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/LitTestCase.py: -------------------------------------------------------------------------------- 1 | import unittest 2 | import Test 3 | 4 | """ 5 | TestCase adaptor for providing a 'unittest' compatible interface to 'lit' tests. 6 | """ 7 | 8 | class UnresolvedError(RuntimeError): 9 | pass 10 | 11 | class LitTestCase(unittest.TestCase): 12 | def __init__(self, test, lit_config): 13 | unittest.TestCase.__init__(self) 14 | self._test = test 15 | self._lit_config = lit_config 16 | 17 | def id(self): 18 | return self._test.getFullName() 19 | 20 | def shortDescription(self): 21 | return self._test.getFullName() 22 | 23 | def runTest(self): 24 | tr, output = self._test.config.test_format.execute( 25 | self._test, self._lit_config) 26 | 27 | if tr is Test.UNRESOLVED: 28 | raise UnresolvedError(output) 29 | elif tr.isFailure: 30 | self.fail(output) 31 | -------------------------------------------------------------------------------- /lib/LoadedElf.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2014, XMOS Ltd., All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "LoadedElf.h" 7 | #include "XE.h" 8 | #include 9 | #include 10 | 11 | using namespace axe; 12 | 13 | LoadedElf::LoadedElf(const XEElfSector *elfSector) : 14 | buf(new char[elfSector->getElfSize()]) 15 | { 16 | if (!elfSector->getElfData(buf)) { 17 | std::cerr << "Error reading ELF data from ELF sector" << std::endl; 18 | std::exit(1); 19 | } 20 | if ((elf = elf_memory(buf, elfSector->getElfSize())) == NULL) { 21 | std::cerr << "Error reading ELF: " << elf_errmsg(-1) << std::endl; 22 | std::exit(1); 23 | } 24 | } 25 | 26 | LoadedElf::~LoadedElf() 27 | { 28 | delete[] buf; 29 | if (elf) 30 | elf_end(elf); 31 | } 32 | -------------------------------------------------------------------------------- /lib/AccessSecondIterator.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _AccessSecondIterator_h_ 7 | #define _AccessSecondIterator_h_ 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | template 15 | struct ValueGetter 16 | { 17 | typedef const typename Iterator::value_type::second_type &result_type; 18 | result_type operator() (const typename Iterator::value_type& p) const { 19 | return p.second; 20 | } 21 | }; 22 | 23 | template using AccessSecondIterator = 24 | boost::transform_iterator< 25 | ValueGetter, Iterator>; 26 | 27 | } // End axe namespace 28 | 29 | #endif // _AccessSecondIterator_h_ 30 | -------------------------------------------------------------------------------- /lib/Exceptions.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Exceptions.h" 7 | 8 | using namespace axe; 9 | 10 | const char *Exceptions::getExceptionName(int type) 11 | { 12 | switch (type) { 13 | case ET_LINK_ERROR: return "LINK_ERROR"; 14 | case ET_ILLEGAL_PC: return "ILLEGAL_PC"; 15 | case ET_ILLEGAL_INSTRUCTION: return "ILLEGAL_INSTRUCTION"; 16 | case ET_ILLEGAL_RESOURCE: return "ILLEGAL_RESOURCE"; 17 | case ET_LOAD_STORE: return "LOAD_STORE"; 18 | case ET_ILLEGAL_PS: return "ILLEGAL_PS"; 19 | case ET_ARITHMETIC: return "ARITHMETIC"; 20 | case ET_ECALL: return "ECALL"; 21 | case ET_RESOURCE_DEP: return "RESOURCE_DEP"; 22 | case ET_KCALL: return "KCALL"; 23 | default: return "Unknown"; 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /test/Resources/ClockBlocks/port_source4.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | 6 | out port clk_out = XS1_PORT_1A; 7 | in port p = XS1_PORT_1B; 8 | clock c = XS1_CLKBLK_1; 9 | clock c2 = XS1_CLKBLK_2; 10 | 11 | int main() { 12 | timer t; 13 | unsigned time; 14 | unsigned diff; 15 | set_clock_div(c2, 10); 16 | configure_out_port(clk_out, c2, 1); 17 | configure_clock_src(c, clk_out); 18 | configure_in_port(p, c); 19 | start_clock(c2); 20 | start_clock(c); 21 | t :> time; 22 | clk_out <: 0; 23 | // This should timeout 24 | select { 25 | case p :> void: 26 | return 1; 27 | case t when timerafter(time+100) :> void: 28 | break; 29 | } 30 | t :> time; 31 | clk_out <: 1; 32 | // This shouldn't timeout 33 | select { 34 | case p :> void: 35 | break; 36 | case t when timerafter(time+100) :> void: 37 | return 2; 38 | } 39 | return 0; 40 | } 41 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/lit.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | # Configuration file for the 'lit' test runner. 4 | 5 | # name: The name of this test suite. 6 | config.name = 'Examples' 7 | 8 | # suffixes: A list of file extensions to treat as test files. 9 | config.suffixes = ['.c', '.cpp', '.m', '.mm', '.ll'] 10 | 11 | # testFormat: The test format to use to interpret tests. 12 | config.test_format = lit.formats.ShTest() 13 | 14 | # test_source_root: The path where tests are located (default is the test suite 15 | # root). 16 | config.test_source_root = None 17 | 18 | # test_exec_root: The path where tests are located (default is the test suite 19 | # root). 20 | config.test_exec_root = None 21 | 22 | # target_triple: Used by ShTest and TclTest formats for XFAIL checks. 23 | config.target_triple = 'foo' 24 | 25 | # available_features: Used by ShTest and TclTest formats for REQUIRES checks. 26 | config.available_features = ['some-feature-name'] 27 | -------------------------------------------------------------------------------- /lib/JIT.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _JIT_h_ 7 | #define _JIT_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | class Thread; 14 | class Core; 15 | class JITImpl; 16 | 17 | class JIT { 18 | JITImpl *pImpl; 19 | public: 20 | JIT(); 21 | JIT(const JIT &) = delete; 22 | ~JIT(); 23 | /// Preallocate global state for the JIT. Normally this state is initialized 24 | /// when the JIT is first used but in a multi-threaded applications it should 25 | /// be preallocated to avoid race conditions. 26 | static void initializeGlobalState(); 27 | void compileBlock(Core &c, uint32_t pc); 28 | bool invalidate(Core &c, uint32_t pc); 29 | }; 30 | 31 | } // End axe namespace 32 | 33 | #endif // _JIT_h_ 34 | -------------------------------------------------------------------------------- /test/Resources/Chanends/not_in_use_junk.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | .text 7 | .align 2 8 | .globl main 9 | main: 10 | getr r0, XS1_RES_TYPE_CHANEND 11 | ldc r11, 0x100 12 | add r1, r0, r11 13 | setd res[r0], r1 14 | // This should be junked since the destination is not in use. 15 | out res[r0], r0 16 | out res[r0], r0 17 | getr r2, XS1_RES_TYPE_CHANEND 18 | eq r11, r1, r2 19 | ecallf r11 20 | // This should still be junked as we haven't ended the previous packet. 21 | out res[r0], r0 22 | out res[r0], r0 23 | outct res[r0], XS1_CT_END 24 | // This message should be received. 25 | out res[r0], r11 26 | outct res[r0], XS1_CT_END 27 | in r2, res[r1] 28 | eq r11, r2, r11 29 | ecallf r11 30 | chkct res[r1], XS1_CT_END 31 | freer res[r0] 32 | freer res[r1] 33 | ldc r0, 0 34 | retsp 0 35 | -------------------------------------------------------------------------------- /test/Resources/Ports/port_counter.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | 6 | out port clk_out = XS1_PORT_1A; 7 | in port p = XS1_PORT_1B; 8 | clock c = XS1_CLKBLK_1; 9 | 10 | static unsigned getts(void port p) 11 | { 12 | unsigned value; 13 | asm("getts %0, res[%1]" : "=r"(value) : "r"(p)); 14 | return value; 15 | } 16 | 17 | int main() { 18 | clk_out <: 0; 19 | configure_clock_src(c, clk_out); 20 | configure_in_port(p, c); 21 | start_clock(c); 22 | clk_out <: 1; 23 | sync(clk_out); 24 | p :> void; 25 | if (getts(p) != 0) { 26 | return 3; 27 | } 28 | clk_out <: 0; 29 | sync(clk_out); 30 | if (getts(p) != 0) { 31 | return 4; 32 | } 33 | clk_out <: 1; 34 | sync(clk_out); 35 | p :> void; 36 | if (getts(p) != 1) { 37 | return 5; 38 | } 39 | clk_out <: 0; 40 | sync(clk_out); 41 | if (getts(p) != 1) { 42 | return 6; 43 | } 44 | return 0; 45 | } 46 | -------------------------------------------------------------------------------- /test/Resources/Chanends/ownership.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .globl main 8 | main: 9 | getr r3, XS1_RES_TYPE_CHANEND 10 | getr r0, XS1_RES_TYPE_SYNC 11 | getst r1, res[r0] 12 | ldap r11, t0 13 | init t[r1]:pc, r11 14 | set t[r1]:r0, r3 15 | getst r2, res[r0] 16 | ldap r11, t1 17 | init t[r2]:pc, r11 18 | set t[r2]:r0, r3 19 | msync res[r0] 20 | msync res[r0] 21 | mjoin res[r0] 22 | freer res[r0] 23 | ldc r0, 0 24 | retsp 0 25 | 26 | t0: 27 | // Setup events on chanend and wait. 28 | eeu res[r0] 29 | ldap r11, success 30 | setv res[r0], r11 31 | ssync 32 | waiteu 33 | 34 | success: 35 | ssync 36 | 37 | t1: 38 | ssync 39 | // These instructions shouldn't change the owner of the chanend. 40 | setd res[r0], r0 41 | out res[r0], r0 42 | // The out should trigger an event on the other thread. 43 | ssync 44 | -------------------------------------------------------------------------------- /lib/RunnableQueue.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "RunnableQueue.h" 7 | 8 | using namespace axe; 9 | 10 | void RunnableQueue::push(Runnable &thread, ticks_t time) 11 | { 12 | if (contains(thread)) { 13 | remove(thread); 14 | } 15 | thread.wakeUpTime = time; 16 | if (!head) { 17 | thread.next = 0; 18 | head = &thread; 19 | } else if (time < head->wakeUpTime) { 20 | head->prev = &thread; 21 | thread.next = head; 22 | head = &thread; 23 | } else { 24 | Runnable *p = head; 25 | while (p->next && time >= p->next->wakeUpTime) 26 | p = p->next; 27 | thread.prev = p; 28 | thread.next = p->next; 29 | if (p->next) 30 | p->next->prev = &thread; 31 | p->next = &thread; 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /lib/SDLEventPoller.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _SDLEventPoller_h_ 7 | #define _SDLEventPoller_h_ 8 | 9 | #include "Runnable.h" 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | namespace axe { 16 | 17 | class RunnableQueue; 18 | 19 | class SDLEventPoller : public Runnable { 20 | RunnableQueue &scheduler; 21 | uint32_t lastPollEvent; 22 | std::vector> listeners; 23 | public: 24 | SDLEventPoller(RunnableQueue &scheduler); 25 | 26 | void addListener(std::function listener) { 27 | listeners.push_back(listener); 28 | } 29 | void run(ticks_t time) override; 30 | }; 31 | 32 | } 33 | 34 | #endif //_SDLEventPoller_h_ 35 | -------------------------------------------------------------------------------- /test/Resources/Ports/buffered_timed_conditional.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback XS1_PORT_1A XS1_PORT_1B 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback XS1_PORT_1A XS1_PORT_1B 5 | 6 | #include 7 | 8 | // A timed conditional input on a buffer port waits until the time and then 9 | // behaves the same as a untimed conditional input. 10 | 11 | buffered out port:1 p = XS1_PORT_1A; 12 | buffered in port:1 q = XS1_PORT_1B; 13 | clock clk = XS1_CLKBLK_1; 14 | 15 | int main() 16 | { 17 | unsigned t; 18 | int x; 19 | configure_in_port(q, clk); 20 | configure_out_port(p, clk, 0); 21 | configure_clock_ref(clk, 10); 22 | par { 23 | { 24 | start_clock(clk); 25 | p @ 100 <: 1; 26 | p @ 200 <: 0; 27 | p @ 300 <: 1; 28 | } 29 | q @ 150 when pinseq(0) :> x @t; 30 | } 31 | if (x != 0) 32 | return 1; 33 | if (t != 200) 34 | return 2; 35 | return 0; 36 | } 37 | -------------------------------------------------------------------------------- /lib/Lock.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Lock.h" 7 | #include "Thread.h" 8 | 9 | using namespace axe; 10 | 11 | Resource::ResOpResult Lock:: 12 | out(Thread &thread, uint32_t value, ticks_t time) 13 | { 14 | // Unpause a thread. 15 | if (!threads.empty()) { 16 | Thread *next = threads.front(); 17 | threads.pop(); 18 | if (time > next->time) 19 | next->time = time; 20 | next->getNextPC(); 21 | next->schedule(); 22 | } else { 23 | held = false; 24 | } 25 | return CONTINUE; 26 | } 27 | 28 | Resource::ResOpResult Lock:: 29 | in(Thread &thread, ticks_t time, uint32_t &value) 30 | { 31 | if (!held) { 32 | held = true; 33 | value = getID(); 34 | return CONTINUE; 35 | } 36 | threads.push(&thread); 37 | return DESCHEDULE; 38 | } 39 | -------------------------------------------------------------------------------- /lib/Register.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Register_h_ 7 | #define _Register_h_ 8 | 9 | namespace axe { 10 | 11 | namespace Register { 12 | enum Reg { 13 | R0, 14 | R1, 15 | R2, 16 | R3, 17 | R4, 18 | R5, 19 | R6, 20 | R7, 21 | R8, 22 | R9, 23 | R10, 24 | R11, 25 | CP, 26 | DP, 27 | SP, 28 | LR, 29 | ET, 30 | ED, 31 | KEP, 32 | KSP, 33 | SPC, 34 | SED, 35 | SSR, 36 | NUM_REGISTERS 37 | }; 38 | } 39 | 40 | extern const char *registerNames[]; 41 | 42 | inline const char *getRegisterName(unsigned RegNum) { 43 | if (RegNum < Register::NUM_REGISTERS) { 44 | return registerNames[RegNum]; 45 | } 46 | return "?"; 47 | } 48 | 49 | } // End axe namespace 50 | 51 | #endif //_Register_h_ 52 | -------------------------------------------------------------------------------- /test/Resources/Ports/port_counter3.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | // Check effect of set_port_sample_delay() on port counter. 5 | 6 | #include 7 | 8 | out port clk_out = XS1_PORT_1A; 9 | in port p = XS1_PORT_1B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | static unsigned getts(void port p) 13 | { 14 | unsigned value; 15 | asm("getts %0, res[%1]" : "=r"(value) : "r"(p)); 16 | return value; 17 | } 18 | 19 | int main() { 20 | clk_out <: 0; 21 | configure_clock_src(c, clk_out); 22 | configure_in_port(p, c); 23 | set_port_sample_delay(p); 24 | start_clock(c); 25 | clk_out <: 1; 26 | sync(clk_out); 27 | clk_out <: 0; 28 | sync(clk_out); 29 | p :> void; 30 | if (getts(p) != 1) { 31 | return 4; 32 | } 33 | clk_out <: 1; 34 | sync(clk_out); 35 | if (getts(p) != 1) { 36 | return 5; 37 | } 38 | clk_out <: 0; 39 | sync(clk_out); 40 | p :> void; 41 | if (getts(p) != 2) { 42 | return 6; 43 | } 44 | return 0; 45 | } 46 | -------------------------------------------------------------------------------- /lib/Property.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Property.h" 7 | 8 | using namespace axe; 9 | 10 | int32_t Property::getAsInteger() const { 11 | assert(descriptor->getType() == PropertyDescriptor::INTEGER); 12 | return static_cast(this)->getValue(); 13 | } 14 | std::string Property::getAsString() const { 15 | assert(descriptor->getType() == PropertyDescriptor::STRING); 16 | return static_cast(this)->getValue(); 17 | } 18 | const PortArg &Property::getAsPort() const { 19 | assert(descriptor->getType() == PropertyDescriptor::PORT); 20 | return static_cast(this)->getValue(); 21 | } 22 | 23 | Properties::~Properties() 24 | { 25 | for (const auto &entry : properties) { 26 | delete entry.second; 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /test/Resources/Ports/buffered_conditional.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback XS1_PORT_8A XS1_PORT_8B 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback XS1_PORT_8A XS1_PORT_8B 5 | 6 | #include 7 | 8 | out port p = XS1_PORT_8A; 9 | buffered in port:32 q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | int main() { 13 | unsigned time; 14 | int tmp, t; 15 | configure_in_port(q, c); 16 | configure_out_port(p, c, 0); 17 | configure_clock_ref(c, 10); 18 | p <: 0x28; 19 | par { 20 | { 21 | start_clock(c); 22 | p <: 0x2c; 23 | p <: 0x54; 24 | p <: 0x99; 25 | p <: 0x12; 26 | p <: 0x34; 27 | p <: 0x56; 28 | p <: 0x78; 29 | p <: 0x9a; 30 | } 31 | { 32 | q when pinseq(0x34) :> tmp @ t; 33 | } 34 | } 35 | if (tmp != 0x34129954) 36 | return 1; 37 | if (t != 6) 38 | return 2; 39 | return 0; 40 | } 41 | -------------------------------------------------------------------------------- /lib/SSwitchCtrlRegs.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _SSwitchCtrlRegs_h_ 7 | #define _SSwitchCtrlRegs_h_ 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | class Node; 15 | 16 | class SSwitchCtrlRegs { 17 | private: 18 | Node *node; 19 | uint32_t scratchReg; 20 | uint32_t clkDividerReg; 21 | std::vector regFlags; 22 | enum RegisterFlags { 23 | REG_READ = 1, 24 | REG_WRITE = 1 << 1, 25 | REG_RW = REG_READ | REG_WRITE 26 | }; 27 | void initReg(unsigned num, uint8_t flags); 28 | public: 29 | SSwitchCtrlRegs(Node *n); 30 | void initRegisters(); 31 | bool read(uint16_t num, uint32_t &result); 32 | bool write(uint16_t num, uint32_t value); 33 | }; 34 | 35 | } // End axe namespace 36 | 37 | #endif //_SSwitchCtrlRegs_h_ 38 | -------------------------------------------------------------------------------- /lib/AXEInitialize.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "AXEInitialize.h" 7 | #include "JIT.h" 8 | #include 9 | #include 10 | #include "registerAllPeripherals.h" 11 | #include "BootSequencer.h" 12 | 13 | using namespace axe; 14 | 15 | void axe::AXEInitialize(bool beLazy) 16 | { 17 | /* 18 | * this initialize the library and check potential ABI mismatches 19 | * between the version it was compiled for and the actual shared 20 | * library used. 21 | */ 22 | LIBXML_TEST_VERSION 23 | registerAllPeripherals(); 24 | if (!beLazy) { 25 | xmlInitParser(); 26 | xsltInit(); 27 | JIT::initializeGlobalState(); 28 | BootSequencer::initializeElfHandling(); 29 | } 30 | } 31 | 32 | void axe::AXECleanup() 33 | { 34 | xsltCleanupGlobals(); 35 | xmlCleanupParser(); 36 | } 37 | -------------------------------------------------------------------------------- /lib/PortCombiner.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortCombiner_ 7 | #define _PortCombiner_ 8 | 9 | #include 10 | #include "PortHandleClockMixin.h" 11 | 12 | namespace axe { 13 | 14 | class PortCombiner final : public PortHandleClockMixin { 15 | uint32_t value; 16 | struct Slice { 17 | Slice(uint32_t mask, unsigned shift, PortInterface *interface) : 18 | mask(mask), shift(shift), interface(interface) {} 19 | uint32_t mask; 20 | unsigned shift; 21 | PortInterface *interface; 22 | }; 23 | std::vector slices; 24 | public: 25 | PortCombiner(RunnableQueue &s); 26 | void seePinsValueChange(uint32_t value, ticks_t time); 27 | void attach(PortInterface *to, unsigned beginOffset, unsigned endOffset); 28 | }; 29 | 30 | } // End axe namespace 31 | 32 | #endif //_PortCombiner_ 33 | -------------------------------------------------------------------------------- /lib/SystemStateWrapper.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _SystemStateWrapper_h 7 | #define _SystemStateWrapper_h 8 | 9 | #include "StopReason.h" 10 | #include "Config.h" 11 | #include 12 | 13 | namespace axe { 14 | 15 | class SystemState; 16 | class Thread; 17 | 18 | class SystemStateWrapper { 19 | std::unique_ptr system; 20 | Thread *lastBreakpointThread; 21 | int lastExitStatus; 22 | ticks_t lastStopTime; 23 | public: 24 | SystemStateWrapper(std::unique_ptr s); 25 | SystemState *getSystemState() { return system.get(); } 26 | Thread *getThreadForLastBreakpoint() { return lastBreakpointThread; } 27 | int getLastExitStatus() const { return lastExitStatus; } 28 | StopReason::Type run(ticks_t numCycles); 29 | }; 30 | 31 | } // End namespace axe 32 | 33 | #endif // _SystemStateWrapper_h 34 | -------------------------------------------------------------------------------- /lib/PortSplitter.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortSplitter_ 7 | #define _PortSplitter_ 8 | 9 | #include 10 | #include "Signal.h" 11 | 12 | namespace axe { 13 | 14 | class PortInterface; 15 | class PortSplitterSlice; 16 | class RunnableQueue; 17 | 18 | class PortSplitter { 19 | RunnableQueue &scheduler; 20 | PortInterface *port; 21 | uint32_t value; 22 | std::map,PortSplitterSlice*> slices; 23 | public: 24 | PortSplitter(RunnableQueue &s, PortInterface *p); 25 | PortSplitter(const PortSplitter &) = delete; 26 | ~PortSplitter(); 27 | PortInterface *getInterface(unsigned beginOffset, unsigned endOffset); 28 | void seePinsValueChange(uint32_t value, ticks_t time, unsigned shift, 29 | uint32_t mask); 30 | }; 31 | 32 | } // End axe namespace 33 | 34 | #endif // _PortSplitter_ 35 | -------------------------------------------------------------------------------- /test/Resources/Ports/port_counter2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | 6 | out port clk_out = XS1_PORT_1A; 7 | out port p = XS1_PORT_1B; 8 | clock c = XS1_CLKBLK_1; 9 | 10 | static unsigned getts(void port p) 11 | { 12 | unsigned value; 13 | asm("getts %0, res[%1]" : "=r"(value) : "r"(p)); 14 | return value; 15 | } 16 | 17 | int main() { 18 | clk_out <: 1; 19 | configure_clock_src(c, clk_out); 20 | configure_out_port(p, c, 0); 21 | p <: 0; 22 | start_clock(c); 23 | clk_out <: 0; 24 | sync(clk_out); 25 | if (getts(p) != 1) { 26 | return 2; 27 | } 28 | p <: 0; 29 | clk_out <: 1; 30 | sync(clk_out); 31 | if (getts(p) != 1) { 32 | return 2; 33 | } 34 | clk_out <: 0; 35 | sync(clk_out); 36 | p <: 0; 37 | if (getts(p) != 2) { 38 | return 3; 39 | } 40 | clk_out <: 1; 41 | sync(clk_out); 42 | if (getts(p) != 2) { 43 | return 4; 44 | } 45 | clk_out <: 0; 46 | sync(clk_out); 47 | p <: 0; 48 | if (getts(p) != 3) { 49 | return 5; 50 | } 51 | return 0; 52 | } 53 | -------------------------------------------------------------------------------- /lib/CRC.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-12, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _CRC_h_ 7 | #define _CRC_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | template uint32_t crc(uint32_t checksum, T data, uint32_t poly) 14 | { 15 | for (unsigned i = 0; i < sizeof(T) * CHAR_BIT; i++) { 16 | int xorBit = (checksum & 1); 17 | 18 | checksum = (checksum >> 1) | ((data & 1) << 31); 19 | data = data >> 1; 20 | 21 | if (xorBit) 22 | checksum = checksum ^ poly; 23 | } 24 | return checksum; 25 | } 26 | 27 | inline uint32_t crc32(uint32_t checksum, uint32_t data, uint32_t poly) 28 | { 29 | return crc(checksum, data, poly); 30 | } 31 | 32 | inline uint32_t crc8(uint32_t checksum, uint8_t data, uint32_t poly) 33 | { 34 | return crc(checksum, data, poly); 35 | } 36 | 37 | } // End axe namespace 38 | 39 | #endif //_CRC_h_ 40 | -------------------------------------------------------------------------------- /utils/genHex/genHex.c: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | int main(int argc, char **argv) 11 | { 12 | FILE *in, *out; 13 | int c; 14 | int needComma; 15 | if (argc != 3) { 16 | fprintf(stderr, "Usage: genHex input output"); 17 | return 1; 18 | } 19 | in = fopen(argv[1], "rb"); 20 | if (!in) { 21 | fprintf(stderr, "failed to open %s: %s", argv[1], strerror(errno)); 22 | return 1; 23 | } 24 | out = fopen(argv[2], "w"); 25 | if (!out) { 26 | fprintf(stderr, "failed to open %s: %s", argv[2], strerror(errno)); 27 | return 1; 28 | } 29 | needComma = 0; 30 | while ((c = getc(in)) != EOF) { 31 | if (needComma) { 32 | fprintf(out, ", "); 33 | } 34 | fprintf(out, "0x%02x", (unsigned)(unsigned char)c); 35 | needComma = 1; 36 | } 37 | return 0; 38 | } 39 | -------------------------------------------------------------------------------- /lib/StopReason.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "StopReason.h" 7 | 8 | using namespace axe; 9 | 10 | StopReason StopReason::getTimeout(ticks_t time) 11 | { 12 | return StopReason(TIMEOUT, time); 13 | } 14 | 15 | StopReason StopReason::getNoRunnableThreads(ticks_t time) 16 | { 17 | return StopReason(NO_RUNNABLE_THREADS, time); 18 | } 19 | 20 | StopReason StopReason::getBreakpoint(ticks_t time, Thread &thread) 21 | { 22 | StopReason retval(BREAKPOINT, time); 23 | retval.thread = &thread; 24 | return retval; 25 | } 26 | 27 | StopReason StopReason::getWatchpoint(ticks_t time, Thread &thread) 28 | { 29 | StopReason retval(WATCHPOINT, time); 30 | retval.thread = &thread; 31 | return retval; 32 | } 33 | 34 | StopReason StopReason::getExit(ticks_t time, int status) 35 | { 36 | StopReason retval(EXIT, time); 37 | retval.status = status; 38 | return retval; 39 | } 40 | -------------------------------------------------------------------------------- /test/Resources/Ports/setpsc.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 5 | 6 | #include 7 | 8 | buffered out port:32 p = XS1_PORT_8A; 9 | buffered in port:32 q = XS1_PORT_8B; 10 | clock c = XS1_CLKBLK_1; 11 | 12 | // Defeat compiler optimizations. 13 | int identity(int x) { 14 | asm("mov %0, %1" : "=r"(x) : "r"(x)); 15 | return x; 16 | } 17 | 18 | int main() { 19 | int val; 20 | int tmp; 21 | configure_in_port(q, c); 22 | configure_out_port(p, c, 0); 23 | configure_clock_ref(c, 10); 24 | start_clock(c); 25 | p @ 10 <: 0x99542c28; 26 | q @ 10 :> val; 27 | val >>= 24; 28 | set_port_shift_count(q, identity(8)); 29 | q :> tmp; 30 | val |= (tmp >> 24) << 8; 31 | set_port_shift_count(q, identity(8)); 32 | q :> tmp; 33 | val |= (tmp >> 24) << 16; 34 | set_port_shift_count(q, identity(8)); 35 | q :> tmp; 36 | val |= (tmp >> 24) << 24; 37 | if (val != 0x99542c28) 38 | return 1; 39 | return 0; 40 | } 41 | -------------------------------------------------------------------------------- /lib/registerAllPeripherals.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "registerAllPeripherals.h" 7 | #include "PeripheralRegistry.h" 8 | #include "UartRx.h" 9 | #include "SDRAM.h" 10 | #include "SPIFlash.h" 11 | #include "EthernetPhy.h" 12 | #include "PeripheralDescriptor.h" 13 | #include "Config.h" 14 | #if AXE_ENABLE_SDL 15 | #include "LCDScreen.h" 16 | #include "PS2Keyboard.h" 17 | #endif 18 | 19 | using namespace axe; 20 | 21 | void axe::registerAllPeripherals() 22 | { 23 | PeripheralRegistry::add(getPeripheralDescriptorUartRx()); 24 | PeripheralRegistry::add(getPeripheralDescriptorSDRAM()); 25 | PeripheralRegistry::add(getPeripheralDescriptorSPIFlash()); 26 | PeripheralRegistry::add(getPeripheralDescriptorEthernetPhy()); 27 | #if AXE_ENABLE_SDL 28 | PeripheralRegistry::add(getPeripheralDescriptorLCDScreen()); 29 | PeripheralRegistry::add(getPeripheralDescriptorPS2Keyboard()); 30 | #endif 31 | } 32 | -------------------------------------------------------------------------------- /lib/BreakpointManager.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "BreakpointManager.h" 7 | #include "Core.h" 8 | 9 | using namespace axe; 10 | 11 | bool BreakpointManager:: 12 | setBreakpoint(Core &c, uint32_t address, BreakpointType type) 13 | { 14 | if (!c.setBreakpoint(address)) 15 | return false; 16 | breakpointInfo[std::make_pair(&c, address)] = type; 17 | return true; 18 | } 19 | 20 | BreakpointType BreakpointManager:: 21 | getBreakpointType(Core &c, uint32_t address) 22 | { 23 | auto entry = breakpointInfo.find(std::make_pair(&c, address)); 24 | if (entry == breakpointInfo.end()) 25 | return BreakpointType::Other; 26 | return entry->second; 27 | } 28 | 29 | void BreakpointManager::unsetBreakpoints() 30 | { 31 | for (const auto &entry : breakpointInfo) { 32 | Core *core = entry.first.first; 33 | core->unsetBreakpoint(entry.first.second); 34 | } 35 | breakpointInfo.clear(); 36 | } 37 | -------------------------------------------------------------------------------- /lib/PeripheralRegistry.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PeripheralRegistry.h" 7 | #include "PeripheralDescriptor.h" 8 | #include 9 | 10 | using namespace axe; 11 | 12 | std::map peripherals; 13 | 14 | void PeripheralRegistry::add(std::unique_ptr p) 15 | { 16 | // TODO fix memory leak. 17 | std::string name = p->getName(); 18 | peripherals.insert(std::make_pair(name, p.release())); 19 | } 20 | 21 | PeripheralDescriptor *PeripheralRegistry::get(const std::string &name) 22 | { 23 | auto it = peripherals.find(name); 24 | if (it == peripherals.end()) 25 | return 0; 26 | return it->second; 27 | } 28 | 29 | PeripheralRegistry::iterator PeripheralRegistry::begin() 30 | { 31 | return iterator(peripherals.begin()); 32 | } 33 | 34 | PeripheralRegistry::iterator PeripheralRegistry::end() 35 | { 36 | return iterator(peripherals.end()); 37 | } 38 | -------------------------------------------------------------------------------- /test/Resources/Ports/set_port_inv.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback PORT_1A PORT_1B 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback PORT_1A PORT_1B 5 | 6 | #include 7 | #include 8 | #define VERIFY(x) do { if(!(x)) { _Exit(1); }} while(0) 9 | 10 | port p = XS1_PORT_1A; 11 | port q = XS1_PORT_1B; 12 | 13 | int main() { 14 | int x; 15 | set_port_inv(p); 16 | // Check driven data is inverted. 17 | p <: 0; 18 | sync(p); 19 | q :> x; 20 | q :> x; 21 | VERIFY(x == 1); 22 | p <: 1; 23 | sync(p); 24 | q :> x; 25 | q :> x; 26 | VERIFY(x == 0); 27 | 28 | p :> int; 29 | // Check sampled data is inverted. 30 | q <: 0; 31 | sync(q); 32 | p :> x; 33 | p :> x; 34 | VERIFY(x == 1); 35 | q <: 1; 36 | sync(q); 37 | p :> x; 38 | p :> x; 39 | VERIFY(x == 0); 40 | 41 | // Check peek returns inverted data. 42 | VERIFY(peek(p) == 0); 43 | 44 | // Check set_port_no_inv disables the inversion. 45 | set_port_no_inv(p); 46 | p :> x; 47 | p :> x; 48 | VERIFY(x == 1); 49 | return 0; 50 | } 51 | -------------------------------------------------------------------------------- /lib/ChanEndpoint.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "ChanEndpoint.h" 7 | 8 | using namespace axe; 9 | 10 | ChanEndpoint::ChanEndpoint() : 11 | junkIncoming(true), 12 | source(0) 13 | { 14 | } 15 | 16 | bool ChanEndpoint::claim(ChanEndpoint *newSource, bool &junkPacket) 17 | { 18 | if (junkIncoming) { 19 | junkPacket = true; 20 | return true; 21 | } 22 | // Check if the route is already open. 23 | if (source == newSource) { 24 | return true; 25 | } 26 | // Check if we are already in the middle of a packet. 27 | if (source) { 28 | queue.push(newSource); 29 | return false; 30 | } 31 | // Claim the channel 32 | source = newSource; 33 | return true; 34 | } 35 | 36 | void ChanEndpoint::release(ticks_t time) 37 | { 38 | if (queue.empty()) { 39 | source = 0; 40 | return; 41 | } 42 | source = queue.front(); 43 | queue.pop(); 44 | source->notifyDestClaimed(time); 45 | } 46 | -------------------------------------------------------------------------------- /lib/SystemStateWrapper.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "SystemStateWrapper.h" 7 | #include "SystemState.h" 8 | 9 | using namespace axe; 10 | 11 | SystemStateWrapper:: 12 | SystemStateWrapper(std::unique_ptr s) : 13 | system(std::move(s)), lastBreakpointThread(0), lastExitStatus(0), lastStopTime(0) { 14 | 15 | } 16 | 17 | StopReason::Type SystemStateWrapper::run(ticks_t numCycles) { 18 | if (numCycles == 0) { 19 | system->clearTimeout(); 20 | } else { 21 | system->setTimeout(lastStopTime + numCycles); 22 | } 23 | StopReason stopReason = system->run(); 24 | lastStopTime = stopReason.getTime(); 25 | switch (stopReason.getType()) { 26 | default: 27 | break; 28 | case StopReason::BREAKPOINT: 29 | lastBreakpointThread = stopReason.getThread(); 30 | break; 31 | case StopReason::EXIT: 32 | lastExitStatus = stopReason.getStatus(); 33 | break; 34 | } 35 | return stopReason.getType(); 36 | } 37 | -------------------------------------------------------------------------------- /lib/PortInterface.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortInterface_h_ 7 | #define _PortInterface_h_ 8 | 9 | #include "Config.h" 10 | 11 | namespace axe { 12 | 13 | struct Signal; 14 | 15 | class PortInterface { 16 | protected: 17 | ~PortInterface(); 18 | public: 19 | virtual void seePinsChange(const Signal &value, ticks_t time) = 0; 20 | }; 21 | 22 | /// Port interface which delgates seePinsChange calls to a member function of 23 | /// another class. 24 | template 25 | class PortInterfaceMemberFuncDelegate : public PortInterface { 26 | T &obj; 27 | void (T::*func)(const Signal &value, ticks_t time); 28 | public: 29 | PortInterfaceMemberFuncDelegate(T &o, void (T::*f)(const Signal &value, ticks_t time)) : 30 | obj(o), 31 | func(f) {} 32 | void seePinsChange(const Signal &value, ticks_t time) override { 33 | (obj.*func)(value, time); 34 | } 35 | }; 36 | 37 | } // End axe namespace 38 | 39 | #endif // _PortInterface_h_ 40 | -------------------------------------------------------------------------------- /test/Resources/Ports/readyOut3.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | #include 8 | 9 | in buffered port:32 p = XS1_PORT_1C; 10 | port readyOut = XS1_PORT_1A; 11 | in buffered port:32 loopback = XS1_PORT_1B; 12 | clock clk = XS1_CLKBLK_1; 13 | 14 | int main() 15 | { 16 | timer t; 17 | unsigned time; 18 | unsigned x; 19 | configure_clock_rate(clk, 100, 6); 20 | configure_in_port_strobed_master(p, readyOut, clk); 21 | configure_in_port(loopback, clk); 22 | t :> time; 23 | par { 24 | p @ 5 + 32 :> void; 25 | { 26 | t when timerafter(time + 100) :> void; 27 | start_clock(clk); 28 | loopback :> x; 29 | loopback :> x; 30 | if (x != 0xffffffe0) 31 | _Exit(1); 32 | loopback :> x; 33 | if (x != 0xffffffff) 34 | _Exit(2); 35 | loopback :> x; 36 | if (x != 0xffffffff) 37 | _Exit(3); 38 | loopback :> x; 39 | if (x != 0x0000001f) 40 | _Exit(4); 41 | } 42 | } 43 | return 0; 44 | } 45 | -------------------------------------------------------------------------------- /lib/PeripheralDescriptor.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PeripheralDescriptor.h" 7 | 8 | using namespace axe; 9 | 10 | PropertyDescriptor &PeripheralDescriptor:: 11 | addProperty(const PropertyDescriptor &p) 12 | { 13 | return properties.insert(std::make_pair(p.getName(), p)).first->second; 14 | } 15 | 16 | const PropertyDescriptor *PeripheralDescriptor:: 17 | getProperty(const std::string &name) const 18 | { 19 | auto it = properties.find(name); 20 | if (it == properties.end()) 21 | return 0; 22 | return &it->second; 23 | } 24 | 25 | PropertyDescriptor PropertyDescriptor::integerProperty(const std::string &name) 26 | { 27 | return PropertyDescriptor(INTEGER, name); 28 | } 29 | 30 | PropertyDescriptor PropertyDescriptor::stringProperty(const std::string &name) 31 | { 32 | return PropertyDescriptor(STRING, name); 33 | } 34 | 35 | PropertyDescriptor PropertyDescriptor::portProperty(const std::string &name) 36 | { 37 | return PropertyDescriptor(PORT, name); 38 | } 39 | -------------------------------------------------------------------------------- /test/Resources/ClockBlocks/port_source3.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | 6 | out port clk_out = XS1_PORT_1A; 7 | out port p = XS1_PORT_1B; 8 | clock c = XS1_CLKBLK_1; 9 | 10 | #define NUM_FALLING 10 11 | #define DELAY 50 12 | // One output will be queued in advance 13 | #define EXPECTED (DELAY * (2 * (NUM_FALLING - 1) - 1)) 14 | #define TOLERANCE 20 15 | 16 | int main() { 17 | timer t; 18 | unsigned t1, t2; 19 | unsigned diff; 20 | clk_out <: 1; 21 | configure_clock_src(c, clk_out); 22 | configure_out_port(p, c, 0); 23 | start_clock(c); 24 | t :> t1; 25 | par { 26 | { 27 | unsigned time = t1; 28 | unsigned value = 0; 29 | timer t; 30 | for (unsigned i = 0; i < (NUM_FALLING * 2); i++) { 31 | t when timerafter(time+= DELAY) :> void; 32 | clk_out <: value; 33 | value = !value; 34 | } 35 | } 36 | { 37 | for (unsigned i = 0; i < NUM_FALLING; i++) { 38 | p <: 0; 39 | } 40 | t :> t2; 41 | } 42 | } 43 | diff = t2 - t1; 44 | if (diff < EXPECTED - TOLERANCE || 45 | diff > EXPECTED + TOLERANCE) 46 | return 1; 47 | return 0; 48 | } 49 | -------------------------------------------------------------------------------- /test/Resources/ClockBlocks/port_source2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | 4 | #include 5 | 6 | out port clk_out = XS1_PORT_1A; 7 | in port clk_in = XS1_PORT_1B; 8 | in port p = XS1_PORT_1C; 9 | clock c = XS1_CLKBLK_1; 10 | 11 | #define NUM_RISING 10 12 | #define DELAY 50 13 | #define EXPECTED (DELAY * 2 * NUM_RISING) 14 | #define TOLERANCE 20 15 | 16 | int main() { 17 | timer t; 18 | unsigned t1, t2; 19 | unsigned diff; 20 | clk_out <: 1; 21 | configure_clock_src(c, clk_in); //12.5MHz 22 | configure_in_port(p, c); 23 | start_clock(c); 24 | t :> t1; 25 | par { 26 | { 27 | unsigned time = t1; 28 | unsigned value = 0; 29 | timer t; 30 | for (unsigned i = 0; i < (NUM_RISING * 2); i++) { 31 | t when timerafter(time+= DELAY) :> void; 32 | clk_out <: value; 33 | value = !value; 34 | } 35 | } 36 | { 37 | for (unsigned i = 0; i < NUM_RISING; i++) { 38 | p :> void; 39 | } 40 | t :> t2; 41 | } 42 | } 43 | diff = t2 - t1; 44 | if (diff < EXPECTED - TOLERANCE || 45 | diff > EXPECTED + TOLERANCE) 46 | return 1; 47 | return 0; 48 | } 49 | -------------------------------------------------------------------------------- /test/Peripherals/uart.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --uart-rx port=0x10200,bitrate=115200 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --uart-rx port=0x10200,bitrate=115200 5 | 6 | #include 7 | #include 8 | #include 9 | #define BIT_RATE 115200 10 | #define BIT_TIME 100000000 / BIT_RATE 11 | 12 | out port TXD = XS1_PORT_1A; 13 | 14 | static void sendByte(out port TXD, unsigned byte) { 15 | unsigned time; 16 | timer t; 17 | t :> time ; 18 | /* output start bit */ 19 | TXD <: 0; 20 | time += BIT_TIME ; 21 | t when timerafter(time) :> void; 22 | /* output data bits */ 23 | for (int i = 0; i < 8; i++) { 24 | TXD <: >> byte; 25 | time += BIT_TIME; 26 | t when timerafter(time) :> void; 27 | } 28 | /* output stop bit */ 29 | TXD <: 1; 30 | time += BIT_TIME ; 31 | t when timerafter(time) :> void; 32 | } 33 | 34 | static void sendBytes(out port TXD, unsigned char bytes[], unsigned length) 35 | { 36 | for (unsigned i = 0; i < length; i++) { 37 | sendByte(TXD, bytes[i]); 38 | } 39 | } 40 | 41 | int main() 42 | { 43 | TXD <: 1; 44 | sendBytes(TXD, "Hello World!\n", 13); 45 | return 0; 46 | } 47 | -------------------------------------------------------------------------------- /lib/Instruction.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Instruction_h_ 7 | #define _Instruction_h_ 8 | 9 | #include "Config.h" 10 | #include "Node.h" 11 | #include "InstFunction.h" 12 | #include 13 | 14 | namespace axe { 15 | 16 | class Core; 17 | class Thread; 18 | enum InstructionOpcode : short; 19 | 20 | typedef InstFunction_t OPCODE_TYPE; 21 | 22 | struct Operands { 23 | uint32_t ops[6]; 24 | }; 25 | 26 | void instructionDecode(const Core &tile, uint32_t addr, 27 | InstructionOpcode &opcode, Operands &operands, 28 | bool ignoreBreakpoints = false); 29 | 30 | void 31 | instructionDecode(uint16_t low, uint16_t high, bool highValid, 32 | InstructionOpcode &opcode, Operands &operands, Node::Type type); 33 | 34 | void 35 | instructionTransform(InstructionOpcode &opc, Operands &operands, 36 | const Core &tile, uint32_t address, bool isDualIssue); 37 | 38 | } // End axe namespace 39 | 40 | #endif //_Instruction_h_ 41 | -------------------------------------------------------------------------------- /lib/SDLEventPoller.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "SDLEventPoller.h" 7 | #include "RunnableQueue.h" 8 | #include "SystemState.h" 9 | #include 10 | #include 11 | 12 | using namespace axe; 13 | 14 | SDLEventPoller::SDLEventPoller(RunnableQueue &scheduler) : 15 | scheduler(scheduler), 16 | lastPollEvent(0) 17 | { 18 | scheduler.push(*this, 0); 19 | } 20 | 21 | void SDLEventPoller::run(ticks_t time) 22 | { 23 | // Don't poll for events more than 25 times a second. 24 | Uint32 hostTime = SDL_GetTicks(); 25 | if (hostTime - lastPollEvent < 1000/25) 26 | return; 27 | lastPollEvent = time; 28 | SDL_Event event; 29 | while (SDL_PollEvent(&event)) { 30 | for (auto listener : listeners) { 31 | listener(&event, time); 32 | } 33 | if (event.type == SDL_QUIT) 34 | throw ExitException(time, 0); 35 | } 36 | if (scheduler.empty()) 37 | return; 38 | const ticks_t updateTicks = 20000; 39 | scheduler.push(*this, scheduler.front().wakeUpTime + updateTicks); 40 | } 41 | -------------------------------------------------------------------------------- /test/Exceptions/trap_info.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: not %sim %t1.xe > %t2.txt 3 | // RUN: cmp %t2.txt %s.expect 4 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | // RUN: not %sim %t1.xe > %t2.txt 6 | // RUN: cmp %t2.txt %s.expect 7 | #include 8 | 9 | .section .trap_info,"",@progbits 10 | 11 | .Ltrap_info_entries_start0: 12 | .word .Ltrap_info_entries_end0-.Ltrap_info_entries_start0 13 | .word 2 // AXE should skip compile unit with unexpected version. 14 | .word trap_loc 15 | .word trap_bar 16 | .Ltrap_info_entries_end0: 17 | 18 | .Ltrap_info_entries_start1: 19 | .word .Ltrap_info_entries_end1-.Ltrap_info_entries_start1 20 | .word 1 21 | .word trap_loc - 2 // This pc doesn't match. 22 | .word trap_bar 23 | .Ltrap_info_entries_end1: 24 | 25 | .Ltrap_info_entries_start2: 26 | .word .Ltrap_info_entries_end2-.Ltrap_info_entries_start2 27 | .word 1 28 | .word trap_loc // This should match. 29 | .word trap_foo 30 | .Ltrap_info_entries_end2: 31 | 32 | .section .trap_info_str,"MS",@progbits 33 | .space 5 // Space to ensure string is at non-zero offset. 34 | trap_foo: 35 | .asciiz"foo" 36 | trap_bar: 37 | .asciiz"bar" 38 | 39 | .text 40 | .globl main 41 | .align 2 42 | main: 43 | ldc r0, 0 44 | trap_loc: 45 | ecallf r0 46 | -------------------------------------------------------------------------------- /test/Resources/Chanends/basic.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .section .cp.rodata, "ac", @progbits 8 | .align 4 9 | const1: 10 | .word 0x3a 11 | const2: 12 | .word 0x1e761921 13 | 14 | .text 15 | .align 2 16 | .globl main 17 | main: 18 | getr r0, XS1_RES_TYPE_CHANEND 19 | getr r1, XS1_RES_TYPE_CHANEND 20 | setd res[r0], r1 21 | setd res[r1], r0 22 | getd r2, res[r0] 23 | eq r2, r2, r1 24 | ecallf r2 25 | ldw r11, cp[const1] 26 | outt res[r0], r11 27 | testct r11, res[r1] 28 | ecallt r11 29 | int r2, res[r1] 30 | ldw r11, cp[const1] 31 | eq r11, r2, r11 32 | ecallf r11 33 | 34 | ldw r11, cp[const1] 35 | outct res[r0], r11 36 | testct r11, res[r1] 37 | ecallf r11 38 | testwct r11, res[r1] 39 | eq r11, r11, 1 40 | ecallf r11 41 | inct r2, res[r1] 42 | ldw r11, cp[const1] 43 | eq r11, r2, r11 44 | ecallf r11 45 | 46 | ldw r11, cp[const2] 47 | out res[r0], r11 48 | testct r11, res[r1] 49 | ecallt r11 50 | testwct r11, res[r1] 51 | ecallt r11 52 | in r2, res[r1] 53 | ldw r11, cp[const2] 54 | eq r11, r2, r11 55 | ecallf r11 56 | 57 | ldc r0, 0 58 | retsp 0 59 | -------------------------------------------------------------------------------- /test/fibonacci.c: -------------------------------------------------------------------------------- 1 | /* 2 | * RUN: xcc -target=XK-1A %s -o %t1.xe 3 | * RUN: %sim %t1.xe 4 | * RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 5 | * RUN: %sim %t1.xe 6 | */ 7 | 8 | /////////////////////////////////////////////////////////// 9 | //recursion 10 | /////////////////////////////////////////////////////////// 11 | 12 | #include "stdlib.h" 13 | #include "stdio.h" 14 | 15 | /////////////////////////////////////////////////////////// 16 | //Main 17 | /////////////////////////////////////////////////////////// 18 | 19 | int main(void) 20 | { 21 | int fibonacci_depth = 80; // The number of fibonacci numbers we will print 22 | int i = 0; // The index of fibonacci number to be printed next 23 | unsigned long long current = 1; // The value of the (i)th fibonacci number 24 | unsigned long long next = 1; // The value of the (i+1)th fibonacci number 25 | unsigned long long twoaway = 0; // The value of the (i+2)th fibonacci number 26 | 27 | printf("\tI \t Fibonacci(I) \n\t=====================\n"); 28 | 29 | for (i=1; i<=fibonacci_depth; i++) 30 | { 31 | printf("\t%d \t %llu\n", i, current); 32 | twoaway = current+next; 33 | current = next; 34 | next = twoaway; 35 | } 36 | 37 | return EXIT_SUCCESS; 38 | } 39 | 40 | -------------------------------------------------------------------------------- /tools/axe/Options.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Options_h_ 7 | #define _Options_h_ 8 | 9 | #include "Config.h" 10 | #include "PortArg.h" 11 | #include 12 | #include 13 | 14 | namespace axe { 15 | 16 | class PeripheralDescriptor; 17 | class Properties; 18 | 19 | typedef std::vector> LoopbackPorts; 20 | 21 | struct Options { 22 | enum BootMode { 23 | BOOT_SIM, 24 | BOOT_SPI 25 | }; 26 | BootMode bootMode; 27 | LoopbackPorts loopbackPorts; 28 | std::vector> peripherals; 29 | const char *file; 30 | std::string rom; 31 | std::string vcdFile; 32 | bool tracing; 33 | bool traceCycles; 34 | bool time; 35 | bool useColour; 36 | bool stats; 37 | bool warnPacketOvertake; 38 | ticks_t maxCycles; 39 | int clientArgc; 40 | char **clientArgv; 41 | 42 | Options(); 43 | ~Options(); 44 | Options(const Options &) = delete; 45 | void parse(int argc, char **argv); 46 | }; 47 | 48 | } // End axe namespace 49 | 50 | #endif // _Options_h_ 51 | -------------------------------------------------------------------------------- /lib/Lock.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Lock_h_ 7 | #define _Lock_h_ 8 | 9 | #include 10 | #include "Resource.h" 11 | 12 | namespace axe { 13 | 14 | class Lock : public Resource { 15 | private: 16 | /// Is the lock currently held by a thread? 17 | bool held; 18 | /// Paused threads. 19 | std::queue threads; 20 | public: 21 | Lock() : Resource(RES_TYPE_LOCK) {} 22 | 23 | bool alloc(Thread &master) override 24 | { 25 | assert(!isInUse() && "Trying to allocate in use lock"); 26 | setInUse(true); 27 | held = false; 28 | while (!threads.empty()) { 29 | threads.pop(); 30 | } 31 | return true; 32 | } 33 | 34 | bool free() override 35 | { 36 | // TODO what if there are still threads paused on the lock? 37 | setInUse(false); 38 | return true; 39 | } 40 | 41 | 42 | ResOpResult in(Thread &thread, ticks_t time, uint32_t &value) override; 43 | ResOpResult out(Thread &thread, uint32_t value, ticks_t time) override; 44 | }; 45 | 46 | } // End axe namespace 47 | 48 | #endif // _Lock_h_ 49 | -------------------------------------------------------------------------------- /lib/Token.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Token_h_ 7 | #define _Token_h_ 8 | 9 | #include 10 | 11 | namespace axe { 12 | 13 | enum ControlTokenValue { 14 | CT_END = 1, 15 | CT_PAUSE = 2, 16 | CT_ACK = 3, 17 | CT_NACK = 4, 18 | CT_WRITEC = 0xc0, 19 | CT_READC = 0xc1 20 | }; 21 | 22 | class Token { 23 | private: 24 | uint8_t value; 25 | bool control; 26 | 27 | public: 28 | Token(uint8_t v = 0, bool c = false) 29 | : value(v), control(c) { } 30 | 31 | bool isControl() const { 32 | return control; 33 | } 34 | 35 | uint8_t getValue() const { 36 | return value; 37 | } 38 | 39 | bool isCtEnd() const { 40 | return control && value == CT_END; 41 | } 42 | 43 | bool isCtPause() const { 44 | return control && value == CT_PAUSE; 45 | } 46 | 47 | operator uint8_t() const { return value; } 48 | 49 | bool operator==(const Token &other) const { 50 | return value == other.value && 51 | control == other.control; 52 | } 53 | }; 54 | 55 | } // End axe namespace 56 | 57 | #endif // _Token_h_ 58 | -------------------------------------------------------------------------------- /test/Options/port_arguments.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback PORT_4A PORT_8B[0:4] --loopback PORT_1A PORT_8B[4] --loopback PORT_1B PORT_8B[5] --loopback PORT_1C PORT_8B[6] --loopback PORT_1D PORT_8B[7] 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback PORT_4A PORT_8B[0:4] --loopback PORT_1A PORT_8B[4] --loopback PORT_1B PORT_8B[5] --loopback PORT_1C PORT_8B[6] --loopback PORT_1D PORT_8B[7] 5 | #include 6 | #include 7 | 8 | #define VERIFY(x) do { if (!(x)) _Exit(1); } while(0) 9 | 10 | port p = XS1_PORT_8B; 11 | port p0_4 = XS1_PORT_4A; 12 | port p4 = XS1_PORT_1A; 13 | port p5 = XS1_PORT_1B; 14 | port p6 = XS1_PORT_1C; 15 | port p7 = XS1_PORT_1D; 16 | 17 | int main() { 18 | int tmp; 19 | p <: 0b01001010; 20 | sync(p); 21 | 22 | p0_4 :> tmp; 23 | VERIFY(tmp == 0b1010); 24 | p4 :> tmp; 25 | VERIFY(tmp == 0); 26 | p5 :> tmp; 27 | VERIFY(tmp == 0); 28 | p6 :> tmp; 29 | VERIFY(tmp == 1); 30 | p7 :> tmp; 31 | VERIFY(tmp == 0); 32 | 33 | p :> void; 34 | p0_4 <: 0b1001; 35 | p4 <: 0b0; 36 | p5 <: 0b1; 37 | p6 <: 0b1; 38 | p7 <: 0b1; 39 | sync(p7); 40 | p :> tmp; 41 | VERIFY(tmp == 0b11101001); 42 | 43 | return 0; 44 | } 45 | -------------------------------------------------------------------------------- /lib/PeripheralNode.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PeripheralNode.h" 7 | 8 | using namespace axe; 9 | 10 | PeripheralNode::PeripheralNode() : Node(Node::XS1_L, 1) 11 | { 12 | // Set the number of node bits to 0 so the switch accepts all messages. 13 | setNodeNumberBits(0); 14 | } 15 | 16 | void PeripheralNode::finalize() 17 | { 18 | // The link is always enabled and in five wire mode. 19 | // TODO this part of the link configuration is hardcoded - we should disallow 20 | // changing it using control register writes. 21 | XLink &xlink = getXLink(0); 22 | xlink.setFiveWire(true); 23 | xlink.setEnabled(true); 24 | 25 | Node::finalize(); 26 | } 27 | 28 | ChanEndpoint *PeripheralNode::getOutgoingChanendDest(ResourceID ID) 29 | { 30 | // All outgoing messages are routed over the link, regardless of the ID. 31 | XLink &xlink = getXLink(0); 32 | if (!xlink.isConnected()) 33 | return nullptr; 34 | return xlink.getDestNode()->getOutgoingChanendDest(ID); 35 | } 36 | 37 | ChanEndpoint *PeripheralNode::getLocalChanendDest(ResourceID ID) 38 | { 39 | return nullptr; 40 | } 41 | -------------------------------------------------------------------------------- /lib/PortCombiner.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PortCombiner.h" 7 | #include "Signal.h" 8 | #include "BitManip.h" 9 | 10 | using namespace axe; 11 | 12 | PortCombiner::PortCombiner(RunnableQueue &scheduler) : 13 | PortHandleClockMixin(scheduler), 14 | value(0) {} 15 | 16 | void PortCombiner::seePinsValueChange(uint32_t newValue, ticks_t time) 17 | { 18 | for (const Slice &slice : slices) { 19 | uint32_t mask = slice.mask; 20 | unsigned shift = slice.shift; 21 | PortInterface *next = slice.interface; 22 | uint32_t oldSliceValue = (value & mask) >> shift; 23 | uint32_t newSliceValue = (newValue & mask) >> shift; 24 | if (newSliceValue != oldSliceValue) { 25 | next->seePinsChange(Signal(newSliceValue), time); 26 | } 27 | } 28 | value = newValue; 29 | } 30 | 31 | void PortCombiner::attach(PortInterface *to, unsigned beginOffset, 32 | unsigned endOffset) 33 | { 34 | unsigned shift = beginOffset; 35 | uint32_t mask = makeMask(endOffset - beginOffset) << shift; 36 | slices.push_back(Slice(mask, shift, to)); 37 | } 38 | -------------------------------------------------------------------------------- /test/Interrupts/kernel.S: -------------------------------------------------------------------------------- 1 | //RUN: xcc -O2 %s -x xc %s -target=XK-1A -o %t1.xe 2 | //RUN: axe %t1.xe 3 | //RUN: xcc -O2 %s -x xc %s -target=XCORE-200-EXPLORER -mno-dual-issue -o %t1.xe 4 | //RUN: axe %t1.xe 5 | 6 | // To test LD/ST{SPC,SSR,SED,ET} 7 | 8 | #ifdef __XC__ 9 | #include 10 | 11 | void bar(chanend c); 12 | 13 | void foo(chanend c) 14 | { 15 | c <: 0xABC; 16 | } 17 | 18 | int main() 19 | { 20 | chan c; 21 | par { 22 | foo(c); 23 | bar(c); 24 | } 25 | return 0; 26 | } 27 | 28 | #else 29 | #include 30 | 31 | .text 32 | .globl bar 33 | .align 4 34 | bar: 35 | 36 | // Set interrupts on the channel 37 | ldap r11, kernel 38 | setv res[r0], r11 39 | setc res[r0], XS1_SETC_IE_MODE_INTERRUPT 40 | eeu res[r0] 41 | setsr XS1_SR_IEBLE_SET(0, 1) 42 | 43 | // Wait for an interrupt 44 | waiteu 45 | 46 | retsp 0 47 | .globl bar.nstackwords 48 | .set bar.nstackwords, 5 49 | 50 | .align 4 51 | kernel: 52 | entsp 5 53 | stw spc, sp[1] 54 | stw ssr, sp[2] 55 | stw sed, sp[3] 56 | stw et, sp[4] 57 | chkct res[r0], XS1_CT_END 58 | outct res[r0], XS1_CT_END 59 | in r11, res[r0] 60 | chkct res[r0], XS1_CT_END 61 | outct res[r0], XS1_CT_END 62 | ldw spc, sp[1] 63 | ldw ssr, sp[2] 64 | ldw sed, sp[3] 65 | ldw et, sp[4] 66 | retsp 5 67 | kret 68 | 69 | #endif 70 | 71 | -------------------------------------------------------------------------------- /test/Resources/ClockBlocks/port_source.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | 4 | #include 5 | #include 6 | 7 | out port clk_out = XS1_PORT_1A; 8 | // out port clk_out = 0x10200; 9 | in port p = XS1_PORT_1B; 10 | // in port p = 0x10000; 11 | clock c = XS1_CLKBLK_1; 12 | // __clock_t c = 0x106; 13 | 14 | #define NUM_RISING 10 15 | #define DELAY 50 16 | #define EXPECTED (DELAY * 2 * NUM_RISING) 17 | #define TOLERANCE 20 18 | 19 | int main() { 20 | timer t; 21 | unsigned t1, t2; 22 | unsigned diff; 23 | clk_out <: 1; 24 | configure_clock_src(c, clk_out); 25 | configure_in_port(p, c); 26 | start_clock(c); 27 | t :> t1; 28 | par { 29 | { 30 | unsigned time = t1; 31 | unsigned value = 0; 32 | timer t; 33 | for (unsigned i = 0; i < (NUM_RISING * 2); i++) { 34 | t when timerafter(time+= DELAY) :> void; 35 | clk_out <: value; 36 | value = !value; 37 | } 38 | } 39 | { 40 | for (unsigned i = 0; i < NUM_RISING; i++) { 41 | p :> void; 42 | } 43 | t :> t2; 44 | } 45 | } 46 | 47 | diff = t2 - t1; 48 | printf("DIFF: %u\n", diff); 49 | printf("EXPECTED: %u\n", EXPECTED); 50 | if (diff < EXPECTED - TOLERANCE || 51 | diff > EXPECTED + TOLERANCE) 52 | return 1; 53 | return 0; 54 | } 55 | -------------------------------------------------------------------------------- /cmake/Modules/FindLibElf.cmake: -------------------------------------------------------------------------------- 1 | # Locate libelf library 2 | # This module defines 3 | # LIBELF_FOUND - System has libelf 4 | # LIBELF_INCLUDE_DIRS - The libelf include directories 5 | # LIBELF_LIBRARIES - The libraries needed to use libelf 6 | 7 | # Note that the expected include convention is 8 | # #include 9 | # and not 10 | # #include 11 | # This is because the libelf includes may live in a location other than 12 | # libelf/ 13 | 14 | find_path(LIBELF_INCLUDE_DIR libelf.h PATH_SUFFIXES libelf) 15 | if("${LIBELF_INCLUDE_DIR}" MATCHES "libelf$") 16 | # If the libelf headers live in a libelf subdirectory then they might 17 | # include each other using the libelf/ prefix. Add the parent 18 | # directory to the list of include directories to make this work. 19 | string(REGEX REPLACE "libelf$" "" LIBELF_INCLUDE_DIRS 20 | "${LIBELF_INCLUDE_DIR}") 21 | set(LIBELF_INCLUDE_DIRS 22 | "${LIBELF_INCLUDE_DIRS}" 23 | "${LIBELF_INCLUDE_DIR}") 24 | else() 25 | set(LIBELF_INCLUDE_DIRS "${LIBELF_INCLUDE_DIR}") 26 | endif() 27 | find_library(LIBELF_LIBRARIES elf) 28 | 29 | include(FindPackageHandleStandardArgs) 30 | # Sets LIBELF_FOUND 31 | find_package_handle_standard_args(LibElf DEFAULT_MSG LIBELF_LIBRARIES LIBELF_INCLUDE_DIRS) 32 | 33 | mark_as_advanced(LIBELF_INCLUDE_DIRS LIBELF_LIBRARIES) 34 | -------------------------------------------------------------------------------- /lib/PortArg.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _PortArg_h 7 | #define _PortArg_h 8 | 9 | #include 10 | #include 11 | 12 | namespace axe { 13 | 14 | class Port; 15 | class SystemState; 16 | class PortAliases; 17 | 18 | class PortArg { 19 | std::string core; 20 | std::string port; 21 | /// Beginning offset of this slice of the port (inclusive). 22 | signed char beginOffset; 23 | /// End offset of this slice of the port (exclusive). 24 | signed char endOffset; 25 | 26 | Port *lookupPort(SystemState &system, const PortAliases &portAliases) const; 27 | public: 28 | PortArg() : beginOffset(0), endOffset(0) {} 29 | PortArg(const std::string &c, const std::string &p, signed char begin, 30 | signed char end) : 31 | core(c), port(p), beginOffset(begin), endOffset(end) {} 32 | static bool parse(const std::string &s, PortArg &arg); 33 | bool lookup(SystemState &system, const PortAliases &portAliases, Port *&p, 34 | unsigned &beginOffset, unsigned &endOffset) const; 35 | void dump(std::ostream &s) const; 36 | }; 37 | 38 | } // End axe namespace 39 | 40 | #endif // _PortArg_h 41 | -------------------------------------------------------------------------------- /test/Exceptions/kcall.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .text 8 | .globl main 9 | .align 2 10 | main: 11 | ldap r11, exception_handler 12 | set kep, r11 13 | 14 | ldc r0, 5 15 | .align 4 16 | kcall 5 17 | .align 4 18 | bu kcall2 19 | bu fail 20 | bu fail 21 | bu fail 22 | bu fail 23 | bu fail 24 | 25 | kcall2: 26 | ldc r0, 0xff 27 | .align 4 28 | kcall 0xff 29 | .align 4 30 | bu kcall3 31 | bu fail 32 | bu fail 33 | bu fail 34 | bu fail 35 | bu fail 36 | 37 | kcall3: 38 | ldc r0, 5 39 | .align 4 40 | kcall r0 41 | .align 4 42 | bu fin 43 | bu fail 44 | bu fail 45 | bu fail 46 | bu fail 47 | bu fail 48 | 49 | fin: 50 | retsp 0 51 | 52 | .align 128 53 | exception_handler: 54 | bu fail 55 | .align 64 56 | kernel_entry: 57 | get r11, et 58 | ldc r1, 15 59 | eq r11, r11, r1 60 | bf r11, fail 61 | 62 | get r11, ed 63 | eq r11, r11, r0 64 | bf r11, fail 65 | ldc r0, 0 66 | 67 | ldaw r3, sp[0] 68 | extsp 1 69 | stw spc, sp[1] 70 | ldw r1, sp[1] 71 | add r1, r1, 4 72 | stw r1, sp[1] 73 | ldw spc, sp[1] 74 | set sp, r3 75 | 76 | kret 77 | 78 | fail: 79 | ldc r0, 0 // OSCALL_EXIT 80 | ldc r1, 1 81 | bu _DoSyscall 82 | clre 83 | waiteu 84 | -------------------------------------------------------------------------------- /test/Targets/u_series.xc.xn: -------------------------------------------------------------------------------- 1 | 2 | 5 | Device 6 | XS1-U8A-64-FB96-C5 Device 7 | 8 | 9 | tileref tile[1] 10 | tileref usb_tile 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | -------------------------------------------------------------------------------- /lib/InstructionHelpers.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-12, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstructionHelpers_h_ 7 | #define _InstructionHelpers_h_ 8 | 9 | #include 10 | #include "Config.h" 11 | 12 | namespace axe { 13 | 14 | class Thread; 15 | class Core; 16 | class ResourceID; 17 | class Resource; 18 | class Synchroniser; 19 | class Thread; 20 | class Chanend; 21 | class Port; 22 | class EventableResource; 23 | 24 | uint32_t exception(Thread &t, uint32_t pc, int et, uint32_t ed); 25 | 26 | Resource *checkResource(Core &state, ResourceID id); 27 | 28 | Synchroniser *checkSync(Core &state, ResourceID id); 29 | 30 | Thread *checkThread(Core &state, ResourceID id); 31 | 32 | Chanend *checkChanend(Core &state, ResourceID id); 33 | 34 | Port *checkPort(Core &state, ResourceID id); 35 | 36 | EventableResource *checkEventableResource(Core &state, ResourceID id); 37 | 38 | bool setClock(Thread &t, ResourceID resID, uint32_t val, ticks_t time); 39 | 40 | bool setReadyInstruction(Thread &t, ResourceID resID, uint32_t val, 41 | ticks_t time); 42 | 43 | bool setProcessorState(Thread &t, uint32_t reg, uint32_t value); 44 | 45 | } // End axe namespace 46 | 47 | #endif // _InstructionHelpers_h_ 48 | -------------------------------------------------------------------------------- /test/Resources/Ports/hold_event_value.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | #include 6 | 7 | .section .dp.data, "awd", @progbits 8 | .align 4 9 | p: 10 | .word XS1_PORT_1A 11 | q: 12 | .word XS1_PORT_1B 13 | c: 14 | .word XS1_CLKBLK_1 15 | 16 | .globl main 17 | main: 18 | entsp 4 19 | stw r4, sp[1] 20 | stw r5, sp[2] 21 | stw r6, sp[3] 22 | 23 | ldw r4, dp[p] 24 | setc res[r4], XS1_SETC_INUSE_ON 25 | ldw r5, dp[q] 26 | setc res[r5], XS1_SETC_INUSE_ON 27 | ldc r11, 0 28 | out res[r5], r11 29 | ldw r6, dp[c] 30 | setc res[r6], XS1_SETC_INUSE_ON 31 | mov r0, r4 32 | mov r1, r6 33 | bl configure_in_port 34 | 35 | mov r0, r6 36 | ldc r1, 10 37 | bl configure_clock_ref 38 | 39 | ldap r11, event 40 | setv res[r4], r11 41 | eeu res[r4] 42 | setsr XS1_SR_EEBLE_SET(0, 1) 43 | 44 | setc res[r6], XS1_SETC_RUN_STARTR 45 | waiteu 46 | 47 | event: 48 | ldc r11, 1 49 | out res[r5], r11 50 | getr r1, XS1_RES_TYPE_TIMER 51 | in r11, res[r1] 52 | ldc r0, 100 53 | add r11, r11, r0 54 | setc res[r1], XS1_SETC_COND_AFTER 55 | setd res[r1], r11 56 | in r11, res[r1] 57 | getts r0, res[r4] 58 | ecallt r0 59 | in r0, res[r4] 60 | ecallt r0 61 | ldw r4, sp[1] 62 | ldw r5, sp[2] 63 | ldw r6, sp[3] 64 | retsp 4 65 | -------------------------------------------------------------------------------- /lib/RunnableQueue.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _RunnableQueue_h_ 7 | #define _RunnableQueue_h_ 8 | 9 | #include "Runnable.h" 10 | #include 11 | 12 | namespace axe { 13 | 14 | class RunnableQueue { 15 | private: 16 | Runnable *head; 17 | public: 18 | RunnableQueue() : head(0) {} 19 | 20 | bool contains(Runnable &thread) const 21 | { 22 | return thread.prev != 0 || &thread == head; 23 | } 24 | 25 | Runnable &front() const 26 | { 27 | return *head; 28 | } 29 | 30 | bool empty() const 31 | { 32 | return !head; 33 | } 34 | 35 | void remove(Runnable &thread) 36 | { 37 | assert(contains(thread)); 38 | if (&thread == head) { 39 | head = thread.next; 40 | } else { 41 | thread.prev->next = thread.next; 42 | } 43 | if (thread.next) 44 | thread.next->prev = thread.prev; 45 | thread.prev = 0; 46 | } 47 | 48 | // Insert a thread into the queue. 49 | void push(Runnable &thread, ticks_t time); 50 | 51 | void pop() 52 | { 53 | assert(!empty()); 54 | if (head->next) { 55 | head->next->prev = 0; 56 | } 57 | head = head->next; 58 | } 59 | }; 60 | 61 | } // End axe namespace 62 | 63 | #endif // _RunnableQueue_h_ 64 | -------------------------------------------------------------------------------- /lib/StatsTracer.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _StatsTracer_h 7 | #define _StatsTracer_h 8 | 9 | #include "Tracer.h" 10 | 11 | namespace axe { 12 | class StatsTracer : public Tracer { 13 | uint64_t numInstructions; 14 | uint64_t numExceptions; 15 | uint64_t numEvents; 16 | uint64_t numInterrupts; 17 | uint64_t numSyscalls; 18 | 19 | void display(void); 20 | public: 21 | StatsTracer(); 22 | ~StatsTracer(); 23 | 24 | void instructionBegin(const Thread &t) override; 25 | void exception(const Thread &t, uint32_t et, uint32_t ed, 26 | uint32_t sed, uint32_t ssr, uint32_t spc) override; 27 | void event(const Thread &t, const EventableResource &res, uint32_t pc, 28 | uint32_t ev) override; 29 | void interrupt(const Thread &t, const EventableResource &res, uint32_t pc, 30 | uint32_t ssr, uint32_t spc, uint32_t sed, 31 | uint32_t ed) override; 32 | void syscall(const Thread &t, const std::string &s) override; 33 | // TODO provide a more sensible interface. 34 | void syscall(const Thread &t, const std::string &s, uint32_t op0) override; 35 | }; 36 | } // End axe namespace 37 | 38 | #endif // _StatsTracer_h 39 | -------------------------------------------------------------------------------- /lib/StopReason.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _StopReason_h_ 7 | #define _StopReason_h_ 8 | 9 | #include 10 | #include "Config.h" 11 | 12 | namespace axe { 13 | 14 | class Thread; 15 | 16 | class StopReason { 17 | public: 18 | enum Type { 19 | BREAKPOINT, 20 | WATCHPOINT, 21 | TIMEOUT, 22 | EXIT, 23 | NO_RUNNABLE_THREADS 24 | }; 25 | private: 26 | Type type; 27 | ticks_t time; 28 | union { 29 | Thread *thread; 30 | int status; 31 | }; 32 | StopReason(Type ty, ticks_t t) : type(ty), time(t) {} 33 | public: 34 | Type getType() const { return type; } 35 | ticks_t getTime() const { return time; } 36 | Thread *getThread() const { 37 | assert(type == BREAKPOINT || type == WATCHPOINT); 38 | return thread; 39 | } 40 | int getStatus() const { 41 | assert(type == EXIT); 42 | return status; 43 | } 44 | 45 | static StopReason getTimeout(ticks_t time); 46 | static StopReason getBreakpoint(ticks_t time, Thread &thread); 47 | static StopReason getWatchpoint(ticks_t time, Thread &thread); 48 | static StopReason getExit(ticks_t time, int status); 49 | static StopReason getNoRunnableThreads(ticks_t time); 50 | }; 51 | 52 | } // End axe namespace 53 | 54 | #endif // _StopReason_h_ 55 | -------------------------------------------------------------------------------- /lib/CheckPacketOvertakeTracer.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _CheckPacketOvertakeTracer_h_ 7 | #define _CheckPacketOvertakeTracer_h_ 8 | 9 | #include "Tracer.h" 10 | #include "Token.h" 11 | #include 12 | #include 13 | 14 | namespace axe { 15 | class ResourceID; 16 | 17 | class CheckPacketOvertakeTracer : public Tracer { 18 | const Thread *thread; 19 | uint32_t pc; 20 | bool processedInstruction; 21 | struct PacketInfo { 22 | std::vector contents; 23 | }; 24 | struct ChanEndInfo { 25 | std::vector outgoingPackets; 26 | }; 27 | std::map chanEndMap; 28 | void reportMismatch(ResourceID resID, const PacketInfo &first, 29 | const PacketInfo &second); 30 | void handleInput(ResourceID resID); 31 | void handleOutput(ResourceID resID, const Token &token); 32 | void processInstruction(const Thread &t, uint32_t pc); 33 | public: 34 | CheckPacketOvertakeTracer(); 35 | 36 | void instructionBegin(const Thread &t) override; 37 | void instructionEnd() override; 38 | void regWrite(Register::Reg reg, uint32_t value) override; 39 | }; 40 | } // End axe namespace 41 | 42 | #endif // _CheckPacketOvertakeTracer_h_ 43 | -------------------------------------------------------------------------------- /thirdparty/lit/lit/ExampleTests/Clang/lit.cfg: -------------------------------------------------------------------------------- 1 | # -*- Python -*- 2 | 3 | # Configuration file for the 'lit' test runner. 4 | 5 | # name: The name of this test suite. 6 | config.name = 'Clang' 7 | 8 | # testFormat: The test format to use to interpret tests. 9 | # 10 | # For now we require '&&' between commands, until they get globally killed and 11 | # the test runner updated. 12 | config.test_format = lit.formats.ShTest(execute_external = True) 13 | 14 | # suffixes: A list of file extensions to treat as test files. 15 | config.suffixes = ['.c', '.cpp', '.m', '.mm'] 16 | 17 | # target_triple: Used by ShTest and TclTest formats for XFAIL checks. 18 | config.target_triple = 'foo' 19 | 20 | ### 21 | 22 | # Discover the 'clang' and 'clangcc' to use. 23 | 24 | import os 25 | 26 | def inferClang(PATH): 27 | # Determine which clang to use. 28 | clang = os.getenv('CLANG') 29 | 30 | # If the user set clang in the environment, definitely use that and don't 31 | # try to validate. 32 | if clang: 33 | return clang 34 | 35 | # Otherwise look in the path. 36 | clang = lit.util.which('clang', PATH) 37 | 38 | if not clang: 39 | lit.fatal("couldn't find 'clang' program, try setting " 40 | "CLANG in your environment") 41 | 42 | return clang 43 | 44 | clang = inferClang(config.environment['PATH']) 45 | if not lit.quiet: 46 | lit.note('using clang: %r' % clang) 47 | config.substitutions.append( (' clang ', ' ' + clang + ' ') ) 48 | -------------------------------------------------------------------------------- /lib/ProcessorNode.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _ProcessorNode_h 7 | #define _ProcessorNode_h 8 | 9 | #include 10 | #include "Node.h" 11 | 12 | namespace axe { 13 | 14 | class Core; 15 | 16 | class ProcessorNode : public Node { 17 | private: 18 | std::vector cores; 19 | long processorMhz; 20 | long referenceMhz; 21 | 22 | void computeCoreNumberBits(); 23 | public: 24 | bool isProcessorNode() override { return true; } 25 | typedef std::vector::iterator core_iterator; 26 | typedef std::vector::const_iterator const_core_iterator; 27 | ProcessorNode(Type t, unsigned numXLinks, long processorMhz, long referenceMhz); 28 | ProcessorNode(const Node &) = delete; 29 | ~ProcessorNode(); 30 | void finalize() override; 31 | void addCore(std::unique_ptr cores); 32 | const std::vector &getCores() const { return cores; } 33 | uint32_t getCoreID(unsigned coreNum) const; 34 | void setNodeID(unsigned value) override; 35 | static bool getTypeFromJtagID(unsigned jtagID, Type &type); 36 | ChanEndpoint *getLocalChanendDest(ResourceID ID) override; 37 | uint32_t getReferenceDivide() { return processorMhz / referenceMhz; }; 38 | }; 39 | 40 | } // End axe namespace 41 | 42 | #endif // _ProcessorNode_h 43 | -------------------------------------------------------------------------------- /utils/genJitGlobalMap/genJitGlobalMap.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "llvm-c/BitReader.h" 7 | #include "llvm-c/Core.h" 8 | #include 9 | #include 10 | #include 11 | 12 | int main(int argc, char **argv) 13 | { 14 | if (argc != 2) { 15 | std::cerr << "Usage: genJitAddrMap input\n"; 16 | std::exit(1); 17 | } 18 | const char *inputFile = argv[1]; 19 | LLVMMemoryBufferRef memBuf; 20 | char *error; 21 | if (LLVMCreateMemoryBufferWithContentsOfFile(inputFile, &memBuf, 22 | &error) != 0) { 23 | std::cerr << "Failed to open " << inputFile << ": " << error << '\n'; 24 | std::free(error); 25 | std::exit(1); 26 | } 27 | LLVMModuleRef module; 28 | if (LLVMParseBitcode(memBuf, &module, &error) != 0) { 29 | std::cerr << "Failed to parse bitcode: " << error << '\n'; 30 | std::free(error); 31 | std::exit(1); 32 | } 33 | std::vector functions; 34 | for (LLVMValueRef it = LLVMGetFirstFunction(module); it; 35 | it = LLVMGetNextFunction(it)) { 36 | if (!LLVMIsDeclaration(it) || LLVMGetIntrinsicID(it) != 0) 37 | continue; 38 | std::cout << "DO_FUNCTION(" << LLVMGetValueName(it) << ")\n"; 39 | } 40 | return 0; 41 | } 42 | -------------------------------------------------------------------------------- /lib/WatchpointManager.h: -------------------------------------------------------------------------------- 1 | #ifndef _WatchpointManager_h_ 2 | #define _WatchpointManager_h_ 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | namespace axe { 9 | 10 | enum class WatchpointType { 11 | UNSET, 12 | READ, 13 | WRITE 14 | }; 15 | 16 | struct Watchpoint { 17 | WatchpointType type; 18 | uint32_t begin; 19 | uint32_t end; 20 | 21 | Watchpoint(WatchpointType type, uint32_t begin, uint32_t end) : 22 | type(type), begin(begin), end(end) {} 23 | 24 | bool operator<(const Watchpoint &other) const { 25 | if (type != other.type) 26 | return type < other.type; 27 | if (begin != other.begin) 28 | return begin < other.begin; 29 | return end < other.end; 30 | } 31 | 32 | bool operator==(const Watchpoint &other) const { 33 | return type == other.type && 34 | begin == other.begin && 35 | end == other.end; 36 | } 37 | }; 38 | 39 | class WatchpointManager { 40 | private: 41 | std::set watchpoints; 42 | std::set::iterator watchpointsIterator; 43 | public: 44 | void setWatchpoint(WatchpointType type, uint32_t lowAddr, uint32_t highAddr); 45 | void unsetWatchpoint(WatchpointType type, uint32_t lowAddr, uint32_t highAddr); 46 | void clearWatchpoints() { watchpoints.clear(); } 47 | bool empty() const { return watchpoints.empty(); } 48 | 49 | bool isWatchpointAddress(WatchpointType t, uint32_t address, uint8_t ldst_size); 50 | }; 51 | 52 | }; // End axe namespace 53 | 54 | #endif //_WatchpointManager_h_ 55 | -------------------------------------------------------------------------------- /test/Resources/Ports/uart2.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10200 5 | 6 | #include 7 | #include 8 | #include 9 | #define BIT_RATE 115200 10 | #define BIT_TIME 100000000 / BIT_RATE 11 | 12 | out port TXD = XS1_PORT_1A; 13 | in port RXD = XS1_PORT_1B; 14 | 15 | unsigned char getByte() 16 | { 17 | return 0xa3; 18 | } 19 | 20 | void transmitter (out port TXD) { 21 | unsigned byte, time; 22 | /* get next byte to transmit */ 23 | byte = getByte(); 24 | /* output start bit */ 25 | TXD <: 0 @ time; 26 | time += BIT_TIME ; 27 | /* output data bits */ 28 | for (int i = 0; i < 8; i++) { 29 | TXD @ time <: >> byte; 30 | time += BIT_TIME; 31 | } 32 | /* output stop bit */ 33 | TXD @ time <: 1; 34 | time += BIT_TIME ; 35 | TXD @ time <: 1; 36 | } 37 | 38 | void putByte(unsigned char b) 39 | { 40 | if (b != 0xa3) 41 | exit(1); 42 | exit(0); 43 | } 44 | 45 | void receiver(in port RXD) { 46 | unsigned byte, time; 47 | /* wait for start bit */ 48 | RXD when pinseq(0) :> void @ time; 49 | time += BIT_TIME / 2; 50 | /* input data bits */ 51 | for (int i = 0; i < 8; i++) { 52 | time += BIT_TIME; 53 | RXD @ time :> >> byte; 54 | } 55 | /* input stop bit */ 56 | time += BIT_TIME; 57 | RXD @ time :> void; 58 | putByte(byte >> 24); 59 | } 60 | 61 | 62 | int main() 63 | { 64 | par { 65 | transmitter(TXD); 66 | receiver(RXD); 67 | } 68 | return 0; 69 | } 70 | -------------------------------------------------------------------------------- /test/Resources/Ports/handshaken.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x80000 0x80100 --loopback 0x10200 0x10600 --loopback 0x10000 0x10300 --loopback 0x10100 0x10400 3 | 4 | #include 5 | 6 | // The following ports should be connected in loopback: 7 | // PORT_8A <-> PORT_8B 8 | // PORT_1A <-> PORT_1E 9 | // PORT_1B <-> PORT_1D 10 | // PORT_1C <-> PORT_1F 11 | 12 | in buffered port:32 p = XS1_PORT_8A; 13 | port p_readyIn = XS1_PORT_1A; 14 | port p_readyOut = XS1_PORT_1B; 15 | port p_outclk = XS1_PORT_1C; 16 | clock p_clk = XS1_CLKBLK_1; 17 | 18 | out buffered port:32 q = XS1_PORT_8B; 19 | port q_readyIn = XS1_PORT_1D; 20 | port q_readyOut = XS1_PORT_1E; 21 | port q_clksrc = XS1_PORT_1F; 22 | clock q_clk = XS1_CLKBLK_2; 23 | 24 | int main() 25 | { 26 | unsigned x; 27 | unsigned time; 28 | configure_clock_rate(p_clk, 100, 24); 29 | configure_in_port_handshake(p, p_readyIn, p_readyOut, p_clk); 30 | configure_port_clock_output(p_outclk, p_clk); 31 | 32 | configure_clock_src(q_clk, q_clksrc); 33 | configure_out_port_handshake(q, q_readyIn, q_readyOut, q_clk, 0); 34 | 35 | start_clock(q_clk); 36 | start_clock(p_clk); 37 | q <: 0x2CC94916; 38 | q <: 0xDE298055; 39 | q <: 0xF6525045; 40 | 41 | p :> x; 42 | if (x != 0x2CC94916) 43 | return 1; 44 | p :> x; 45 | if (x != 0xDE298055) 46 | return 2; 47 | p :> x; 48 | if (x != 0xF6525045) 49 | return 3; 50 | 51 | q @ 32 <: 0xCC2B4EF9; 52 | p :> x @ time; 53 | if (x != 0xCC2B4EF9) 54 | return 3; 55 | if (time != 35) 56 | return 4; 57 | return 0; 58 | } 59 | -------------------------------------------------------------------------------- /lib/Config.h.in: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Config_h_ 7 | #define _Config_h_ 8 | 9 | #include 10 | 11 | #cmakedefine01 AXE_ENABLE_SDL 12 | 13 | #cmakedefine01 AXE_ENABLE_JIT 14 | 15 | /// Number of threads per core. 16 | #define NUM_THREADS 8 17 | 18 | /// Number of synchronisers per core. 19 | // TODO Check number. 20 | #define NUM_SYNCS 8 21 | 22 | /// Number of locks per core. 23 | #define NUM_LOCKS 4 24 | 25 | /// Number of timers per core. 26 | #define NUM_TIMERS 10 27 | 28 | /// Number of channel ends per core. 29 | #define NUM_CHANENDS 32 30 | 31 | /// Number of clock blocks per core. 32 | #define NUM_CLKBLKS 6 33 | 34 | #define NUM_1BIT_PORTS 16 35 | #define NUM_4BIT_PORTS 6 36 | #define NUM_8BIT_PORTS 4 37 | #define NUM_16BIT_PORTS 4 38 | #define NUM_32BIT_PORTS 2 39 | #define NUM_PORTS \ 40 | (NUM_1BIT_PORTS + NUM_4BIT_PORTS + NUM_8BIT_PORTS +\ 41 | NUM_16BIT_PORTS + NUM_32BIT_PORTS) 42 | 43 | /// Log base 2 of memory size in bytes. 44 | #define RAM_SIZE_LOG 16 45 | 46 | /// Default size of ram in bytes 47 | #define RAM_SIZE (1 << RAM_SIZE_LOG) 48 | /// Default ram base 49 | #define RAM_BASE RAM_SIZE 50 | 51 | /// Size of the (input) buffer in a chanend. 52 | #define CHANEND_BUFFER_SIZE 8 53 | 54 | /// Number of processor cycles per 100MHz timer tick 55 | #define CYCLES_PER_TICK 4 56 | 57 | typedef uint64_t ticks_t; 58 | 59 | #endif // _Config_h_ 60 | -------------------------------------------------------------------------------- /lib/Endianness.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Endianness_h_ 7 | #define _Endianness_h_ 8 | 9 | #include 10 | #include 11 | #include 12 | #include "BitManip.h" 13 | 14 | #if defined(BOOST_LITTLE_ENDIAN) 15 | #define HOST_LITTLE_ENDIAN 1 16 | #elif defined(BOOST_BIG_ENDIAN) 17 | #define HOST_LITTLE_ENDIAN 0 18 | #else 19 | #error "Unknown endianness" 20 | #endif 21 | 22 | namespace axe { 23 | 24 | namespace endianness { 25 | inline uint32_t read32le(const uint8_t *p) { 26 | uint32_t val; 27 | std::memcpy(&val, p, sizeof(val)); 28 | if (!HOST_LITTLE_ENDIAN) 29 | val = bswap32(val); 30 | return val; 31 | } 32 | 33 | inline uint16_t read16le(const uint8_t *p) { 34 | if (HOST_LITTLE_ENDIAN) { 35 | uint16_t val; 36 | std::memcpy(&val, p, sizeof(val)); 37 | return val; 38 | } 39 | return p[0] | (p[1] << 8); 40 | } 41 | 42 | inline void write32le(uint8_t *p, uint32_t val) { 43 | if (!HOST_LITTLE_ENDIAN) 44 | val = bswap32(val); 45 | std::memcpy(p, &val, sizeof(val)); 46 | } 47 | 48 | inline void write16le(uint8_t *p, uint16_t val) { 49 | if (HOST_LITTLE_ENDIAN) { 50 | std::memcpy(p, &val, sizeof(val)); 51 | return; 52 | } 53 | p[0] = val; 54 | p[1] = val >> 8; 55 | } 56 | } 57 | 58 | } // End axe namespace 59 | 60 | #endif // _Endianness_h_ 61 | -------------------------------------------------------------------------------- /test/Exceptions/illegal_resource.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s %exception_expect -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s %exception_expect -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | .section .dp.data,"awd",@progbits 7 | .align 4 8 | p: 9 | .word XS1_PORT_1A 10 | clk: 11 | .word XS1_CLKBLK_1 12 | 13 | .text 14 | .globl main 15 | .align 2 16 | main: 17 | entsp 1 18 | // Check out of range pin delay causes exception 19 | ldw r4, dp[p] 20 | setc res[r4], XS1_SETC_INUSE_ON 21 | ldc r0, XS1_ET_ILLEGAL_RESOURCE 22 | mov r1, r4 23 | bl exception_expect 24 | setc res[r4], \ 25 | XS1_SETC_LMODE_SET(0, XS1_SETC_LMODE_PIN_DELAY) | \ 26 | XS1_SETC_MODE_SET(0, XS1_SETC_MODE_LONG) | \ 27 | XS1_SETC_VALUE_SET(0, 6) 28 | bl exception_check 29 | 30 | // Check setting rise / fall delay on running clock causes exception. 31 | ldw r4, dp[clk] 32 | setc res[r4], XS1_SETC_INUSE_ON 33 | setc res[r4], XS1_SETC_RUN_STARTR 34 | ldc r0, XS1_ET_ILLEGAL_RESOURCE 35 | mov r1, r4 36 | bl exception_expect 37 | setc res[r4], \ 38 | XS1_SETC_LMODE_SET(0, XS1_SETC_LMODE_RISE_DELAY) | \ 39 | XS1_SETC_MODE_SET(0, XS1_SETC_MODE_LONG) | \ 40 | XS1_SETC_VALUE_SET(0, 6) 41 | bl exception_check 42 | 43 | ldc r0, XS1_ET_ILLEGAL_RESOURCE 44 | mov r1, r4 45 | bl exception_expect 46 | setc res[r4], \ 47 | XS1_SETC_LMODE_SET(0, XS1_SETC_LMODE_FALL_DELAY) | \ 48 | XS1_SETC_MODE_SET(0, XS1_SETC_MODE_LONG) | \ 49 | XS1_SETC_VALUE_SET(0, 6) 50 | bl exception_check 51 | 52 | ldc r0, 0 53 | retsp 1 54 | -------------------------------------------------------------------------------- /lib/BootSequencer.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _BootSequencer_h 7 | #define _BootSequencer_h 8 | 9 | #include 10 | #include 11 | #include "BreakpointManager.h" 12 | 13 | namespace axe { 14 | 15 | class Core; 16 | class SyscallHandler; 17 | class SystemState; 18 | class XEElfSector; 19 | class BootSequenceStep; 20 | class XE; 21 | 22 | class BootSequencer { 23 | SystemState &sys; 24 | BreakpointManager breakpointManager; 25 | SyscallHandler *syscallHandler; 26 | std::vector steps; 27 | void setEntryPointToRom(); 28 | void eraseAllButLastImage(); 29 | void setLoadImages(bool value); 30 | public: 31 | BootSequencer(SystemState &s); 32 | BootSequencer(const BootSequencer &) = delete; 33 | ~BootSequencer(); 34 | void addElf(Core *c, const XEElfSector *elfSector); 35 | void addSchedule(Core *c, uint32_t address); 36 | void addRun(unsigned numDoneSyscalls); 37 | void populateFromXE(XE &xe); 38 | void adjustForSPIBoot(); 39 | int execute(); 40 | SyscallHandler* getSyscallHandler(); 41 | /// Initialize ELF handling global state. Normally this state is initialized 42 | /// when it is first used but in a multi-threaded applications it may need to 43 | /// be initialized earier to prevent avoid race conditions. 44 | static void initializeElfHandling(); 45 | }; 46 | 47 | } // End axe namespace 48 | 49 | #endif // _BootSequencer_h 50 | -------------------------------------------------------------------------------- /lib/InstructionOpcode.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstructionOpcode_h_ 7 | #define _InstructionOpcode_h_ 8 | 9 | namespace axe { 10 | 11 | /// Below are all the instructions supported by the interpreter. 12 | /// The instructions match those of the XCore except where noted below. 13 | /// 14 | /// The operand for the relative branch instructions (bt, bf, bu, bl) is the 15 | /// absolute translated pc value. There are two versions of each of these 16 | /// instructions: one where the branch target is known to be legal 17 | /// and one where it is known to be illegal. 18 | /// 19 | /// There are two versions of the shift immediate instructions shr, ashr, shl, 20 | /// one where the immediate is equal to 32 and one where it is less than 32. 21 | /// 22 | /// The value for bitp operands is the decoded bitp value, except for 23 | /// MKMSK_rus where the operand is the mask to use. The value for scaled 24 | /// operands is the scaled value. 25 | /// 26 | /// Finally there exist a number of additional pseduo instructions which don't 27 | /// exist in the XCore instruction set which the interpreter uses. 28 | enum InstructionOpcode : short { 29 | #define EMIT_INSTRUCTION_LIST 30 | #define DO_INSTRUCTION(inst) inst, 31 | #include "InstructionGenOutput.inc" 32 | #undef EMIT_INSTRUCTION_LIST 33 | #undef DO_INSTRUCTION 34 | }; 35 | 36 | } // End axe namespace 37 | 38 | #endif // _InstructionOpcode_h_ 39 | -------------------------------------------------------------------------------- /lib/Timer.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _Timer_h_ 7 | #define _Timer_h_ 8 | 9 | #include "Resource.h" 10 | 11 | namespace axe { 12 | 13 | class Timer : public EventableResource { 14 | private: 15 | bool after; 16 | uint32_t data; 17 | /// Thread paused on an input instruction. 18 | Thread *pausedIn; 19 | 20 | /// Return whether the condition is met for the specified time. 21 | bool conditionMet(ticks_t time) const; 22 | public: 23 | Timer() : 24 | EventableResource(RES_TYPE_TIMER), 25 | pausedIn(0) {} 26 | 27 | bool alloc(Thread &t) override 28 | { 29 | assert(!isInUse() && "Trying to allocate in use timer"); 30 | after = false; 31 | data = 0; 32 | eventableSetInUseOn(t); 33 | return true; 34 | } 35 | 36 | bool free() override 37 | { 38 | eventableSetInUseOff(); 39 | return true; 40 | } 41 | 42 | bool setCondition(Thread &thread, Condition c, ticks_t time) override; 43 | bool setData(Thread &thread, uint32_t d, ticks_t time) override; 44 | bool getData(Thread &thread, uint32_t &value, ticks_t time) override; 45 | 46 | ResOpResult in(Thread &thread, ticks_t time, uint32_t &val) override; 47 | 48 | /// Returns the earliest time at which the timer will become ready. 49 | ticks_t getEarliestReadyTime(ticks_t time) const; 50 | 51 | void run(ticks_t time) override; 52 | 53 | protected: 54 | bool seeEventEnable(ticks_t time) override; 55 | }; 56 | 57 | } // End axe namespace 58 | 59 | #endif // _Timer_h_ 60 | -------------------------------------------------------------------------------- /utils/not/not.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifdef _WIN32 7 | #include "Windows.h" 8 | #else 9 | #include 10 | #include 11 | #endif 12 | 13 | #include 14 | #include 15 | 16 | int main(int argc, char **argv) 17 | { 18 | #ifdef _WIN32 19 | std::string args; 20 | bool needSpace = false; 21 | for (int i = 1; i < argc; ++i) { 22 | if (needSpace) { 23 | args += ' '; 24 | } 25 | args += argv[i]; 26 | needSpace = true; 27 | } 28 | STARTUPINFO sInfo; 29 | GetStartupInfo(&sInfo); 30 | PROCESS_INFORMATION pInfo; 31 | if (!CreateProcess(NULL, (LPSTR)args.c_str(), NULL, NULL, FALSE, 0, NULL, 32 | NULL, &sInfo, &pInfo)) { 33 | std::fprintf(stderr, "CreateProcess failed\n"); 34 | return 1; 35 | } 36 | WaitForSingleObject(pInfo.hProcess, INFINITE); 37 | DWORD status; 38 | GetExitCodeProcess(pInfo.hProcess, &status); 39 | CloseHandle(pInfo.hProcess); 40 | CloseHandle(pInfo.hThread); 41 | return status ? 0 : 1; 42 | #else 43 | pid_t child_pid = fork(); 44 | switch (child_pid) { 45 | case -1: 46 | std::perror("fork failed"); 47 | return 1; 48 | case 0: 49 | // Child 50 | execvp(argv[1], &argv[1]); 51 | std::perror("execvp failed"); 52 | return 1; 53 | default: 54 | // Parent 55 | int status = 0; 56 | if (waitpid(child_pid, &status, 0) != child_pid) { 57 | std::perror("waitpid failed"); 58 | } 59 | return status ? 0 : 1; 60 | } 61 | #endif 62 | } 63 | -------------------------------------------------------------------------------- /lib/InstructionMacrosCommon.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstructionMacrosCommon_h_ 7 | #define _InstructionMacrosCommon_h_ 8 | 9 | #define LOAD_RAM_WORD(addr) CORE.loadRamWord(addr) 10 | #define LOAD_RAM_SHORT(addr) CORE.loadRamShort(addr) 11 | #define LOAD_RAM_BYTE(addr) CORE.loadRamByte(addr) 12 | #define LOAD_ROM_WORD(addr) CORE.loadRomWord(addr) 13 | #define LOAD_ROM_SHORT(addr) CORE.loadRomShort(addr) 14 | #define LOAD_ROM_BYTE(addr) CORE.loadRomByte(addr) 15 | #define INVALIDATE_WORD(addr) CORE.invalidateWord(addr) 16 | #define INVALIDATE_SHORT(addr) CORE.invalidateShort(addr) 17 | #define INVALIDATE_BYTE(addr) CORE.invalidateByte(addr) 18 | #define STORE_WORD(value, addr) CORE.storeWord(value, addr) 19 | #define STORE_SHORT(value, addr) CORE.storeShort(value, addr) 20 | #define STORE_BYTE(value, addr) CORE.storeByte(value, addr) 21 | #define CHECK_ADDR_RAM_BYTE(addr) CHECK_ADDR_RAM(addr) 22 | #define CHECK_ADDR_RAM_SHORT(addr) (!((addr) & 1) && CHECK_ADDR_RAM(addr)) 23 | #define CHECK_ADDR_RAM_WORD(addr) (!((addr) & 3) && CHECK_ADDR_RAM(addr)) 24 | #define CHECK_ADDR_ROM(addr) \ 25 | ((uint32_t(addr) - CORE.getRomBase()) < CORE.getRomSize()) 26 | #define CHECK_ADDR_ROM_BYTE(addr) CHECK_ADDR_ROM(addr) 27 | #define CHECK_ADDR_ROM_SHORT(addr) (!((addr) & 1) && CHECK_ADDR_ROM(addr)) 28 | #define CHECK_ADDR_ROM_WORD(addr) (!((addr) & 3) && CHECK_ADDR_ROM(addr)) 29 | #define FROM_PC(addr) THREAD.fromPc(addr) 30 | #define TO_PC(addr) THREAD.toPc(addr) 31 | #define TIME THREAD.time 32 | 33 | #endif //_InstructionMacrosCommon_h_ 34 | -------------------------------------------------------------------------------- /lib/JITOptimize.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _JITOptimize_h_ 7 | #define _JITOptimize_h_ 8 | 9 | #include 10 | #include 11 | #include 12 | #include "Instruction.h" 13 | #include "Register.h" 14 | 15 | namespace axe { 16 | 17 | // Let x = baseReg + scale + offsetReg + offsetImm 18 | class MemoryCheck { 19 | public: 20 | enum Type { 21 | CheckAlignment = 1 << 0, 22 | CheckAddress = 1 << 1, 23 | CheckInvalidation = 1 << 2, 24 | }; 25 | private: 26 | unsigned size; 27 | Register::Reg baseReg; 28 | unsigned scale; 29 | Register::Reg offsetReg; 30 | uint32_t offsetImm; 31 | /// Bitwise OR of MemoryCheck::Type. 32 | unsigned flags; 33 | public: 34 | MemoryCheck(unsigned Size, Register::Reg base, unsigned s, 35 | Register::Reg offset, uint32_t offsetI, unsigned f) : 36 | size(Size), 37 | baseReg(base), 38 | scale(s), 39 | offsetReg(offset), 40 | offsetImm(offsetI), 41 | flags(f) {} 42 | 43 | unsigned getSize() const { return size; } 44 | Register::Reg getBaseReg() const { return baseReg; } 45 | unsigned getScale() const { return scale; } 46 | Register::Reg getOffsetReg() const { return offsetReg; } 47 | uint32_t getOffsetImm() const { return offsetImm; } 48 | unsigned getFlags() const { return flags; } 49 | }; 50 | 51 | void placeMemoryChecks(std::vector &opcode, 52 | std::vector &operands, 53 | std::queue> &checks); 54 | 55 | } // End axe namespace 56 | 57 | #endif // _JITOptimize_h_ 58 | -------------------------------------------------------------------------------- /test/Resources/Ports/uart.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback XS1_PORT_1A XS1_PORT_1B 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback XS1_PORT_1A XS1_PORT_1B 5 | 6 | #include 7 | #include 8 | #include 9 | #define BIT_RATE 115200 10 | #define BIT_TIME 100000000 / BIT_RATE 11 | 12 | out port TXD = XS1_PORT_1A; 13 | in port RXD = XS1_PORT_1B; 14 | 15 | unsigned char getByte() 16 | { 17 | return 0xa3; 18 | } 19 | 20 | void transmitter (out port TXD) { 21 | unsigned byte, time; 22 | timer t; 23 | /* get next byte to transmit */ 24 | byte = getByte(); 25 | t :> time ; 26 | /* output start bit */ 27 | TXD <: 0; 28 | time += BIT_TIME ; 29 | t when timerafter(time) :> void; 30 | /* output data bits */ 31 | for (int i = 0; i < 8; i++) { 32 | TXD <: >> byte; 33 | time += BIT_TIME; 34 | t when timerafter(time) :> void; 35 | } 36 | /* output stop bit */ 37 | TXD <: 1; 38 | time += BIT_TIME ; 39 | t when timerafter(time) :> void; 40 | } 41 | 42 | void putByte(unsigned char b) 43 | { 44 | if (b != 0xa3) 45 | exit(1); 46 | exit(0); 47 | } 48 | 49 | void receiver(in port RXD) { 50 | unsigned byte, time; 51 | timer t; 52 | /* wait for start bit */ 53 | RXD when pinseq(0) :> void; 54 | t :> time; 55 | time += BIT_TIME / 2; 56 | /* input data bits */ 57 | for (int i = 0; i < 8; i++) { 58 | time += BIT_TIME; 59 | t when timerafter(time) :> void; 60 | RXD :> >> byte; 61 | } 62 | /* input stop bit */ 63 | time += BIT_TIME; 64 | t when timerafter(time) :> void; 65 | RXD :> void; 66 | putByte(byte >> 24); 67 | } 68 | 69 | 70 | int main() 71 | { 72 | par { 73 | transmitter(TXD); 74 | receiver(RXD); 75 | } 76 | return 0; 77 | } 78 | -------------------------------------------------------------------------------- /test/fibonacci.c.expect: -------------------------------------------------------------------------------- 1 | I Fibonacci(I) 2 | ===================== 3 | 1 1 4 | 2 1 5 | 3 2 6 | 4 3 7 | 5 5 8 | 6 8 9 | 7 13 10 | 8 21 11 | 9 34 12 | 10 55 13 | 11 89 14 | 12 144 15 | 13 233 16 | 14 377 17 | 15 610 18 | 16 987 19 | 17 1597 20 | 18 2584 21 | 19 4181 22 | 20 6765 23 | 21 10946 24 | 22 17711 25 | 23 28657 26 | 24 46368 27 | 25 75025 28 | 26 121393 29 | 27 196418 30 | 28 317811 31 | 29 514229 32 | 30 832040 33 | 31 1346269 34 | 32 2178309 35 | 33 3524578 36 | 34 5702887 37 | 35 9227465 38 | 36 14930352 39 | 37 24157817 40 | 38 39088169 41 | 39 63245986 42 | 40 102334155 43 | 41 165580141 44 | 42 267914296 45 | 43 433494437 46 | 44 701408733 47 | 45 1134903170 48 | 46 1836311903 49 | 47 2971215073 50 | 48 4807526976 51 | 49 7778742049 52 | 50 12586269025 53 | 51 20365011074 54 | 52 32951280099 55 | 53 53316291173 56 | 54 86267571272 57 | 55 139583862445 58 | 56 225851433717 59 | 57 365435296162 60 | 58 591286729879 61 | 59 956722026041 62 | 60 1548008755920 63 | 61 2504730781961 64 | 62 4052739537881 65 | 63 6557470319842 66 | 64 10610209857723 67 | 65 17167680177565 68 | 66 27777890035288 69 | 67 44945570212853 70 | 68 72723460248141 71 | 69 117669030460994 72 | 70 190392490709135 73 | 71 308061521170129 74 | 72 498454011879264 75 | 73 806515533049393 76 | 74 1304969544928657 77 | 75 2111485077978050 78 | 76 3416454622906707 79 | 77 5527939700884757 80 | 78 8944394323791464 81 | 79 14472334024676221 82 | 80 23416728348467685 83 | -------------------------------------------------------------------------------- /lib/InstructionProperties.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _InstructionProperties_h_ 7 | #define _InstructionProperties_h_ 8 | 9 | #include "Register.h" 10 | 11 | namespace axe { 12 | 13 | namespace OperandProperties { 14 | enum OpType { 15 | in, 16 | out, 17 | inout, 18 | imm 19 | }; 20 | } 21 | 22 | struct InstructionProperties { 23 | enum Flags { 24 | MAY_BRANCH = 1 << 0, 25 | MAY_YIELD = 1 << 1, 26 | MAY_DESCHEDULE = 1 << 2, 27 | MAY_END_TRACE = 1 << 3, 28 | MEM_CHECK_OPT_ENABLED = 1 << 4 29 | }; 30 | const char *function; 31 | OperandProperties::OpType *ops; 32 | Register::Reg *implicitOps; 33 | unsigned char size; 34 | unsigned char numOperands; 35 | unsigned char numImplicitOperands; 36 | unsigned char flags; 37 | bool mayBranch() const { return flags & MAY_BRANCH; } 38 | bool mayYield() const { return flags & MAY_YIELD; } 39 | bool mayDeschedule() const { return flags & MAY_DESCHEDULE; } 40 | bool mayEndTrace() const { return flags & MAY_END_TRACE; } 41 | bool memCheckHoistingOptEnabled() const { 42 | return flags & MEM_CHECK_OPT_ENABLED; 43 | } 44 | unsigned getNumOperands() const { return numOperands; } 45 | unsigned getNumExplicitOperands() const { 46 | return numOperands - numImplicitOperands; 47 | } 48 | OperandProperties::OpType getOperandType(unsigned i) const { 49 | return ops[i]; 50 | } 51 | Register::Reg getImplicitOperand(unsigned i) const { 52 | return implicitOps[i]; 53 | } 54 | }; 55 | 56 | extern InstructionProperties instructionProperties[]; 57 | 58 | } // End axe namespace 59 | 60 | #endif //_InstructionProperties_h_ 61 | -------------------------------------------------------------------------------- /test/SystemCalls/argv.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s -o %t1.xe 2 | // RUN: %sim --args %t1.xe hello world 3 | 4 | .globl main 5 | 6 | .set buflen, (_buffer_end - _buffer) 7 | 8 | .align 2 9 | main: 10 | entsp 1 11 | 12 | // System call should return -2 if the buffer is too small. 13 | ldc r0, 13 14 | ldaw r1, dp[_buffer] 15 | ldc r2, 4 16 | bl _DoSyscall 17 | add r0, r0, 2 18 | ecallt r0 19 | 20 | // Otherwise it should return argc and populate the buffer with the command 21 | // line args. 22 | ldc r0, 13 23 | ldaw r1, dp[_buffer] 24 | ldc r2, buflen 25 | bl _DoSyscall 26 | 27 | eq r0, r0, 3 // argc=3 28 | ecallf r0 29 | 30 | ldaw r4, dp[_buffer] 31 | eq r0, r1, r4 // argv[] is at start of buffer 32 | ecallf r0 33 | ldc r5, 4*4 // sizeof(argv[]) including null terminator 34 | add r5, r4, r5 // next free byte = &argv[argc+1] 35 | 36 | ldw r0, r4[0] // argv[0] 37 | eq r1, r0, r5 // = next free byte 38 | ecallf r1 39 | bl strlen // strlen(argv[0]) 40 | add r5, r5, r0 41 | add r5, r5, 1 // next free byte 42 | 43 | ldw r0, r4[1] // argv[1] 44 | eq r1, r0, r5 // = next free byte 45 | ecallf r1 46 | ldaw r1, dp[_arg1] 47 | bl strcmp // argv[1] == "hello" 48 | ecallt r0 49 | ldw r0, r4[1] // argv[1] 50 | bl strlen // strlen(argv[1]) 51 | add r5, r5, r0 52 | add r5, r5, 1 // next free byte 53 | 54 | ldw r0, r4[2] // argv[2] 55 | eq r1, r0, r5 // = next free byte 56 | ecallf r1 57 | ldaw r1, dp[_arg2] 58 | bl strcmp // argv[2] == "world" 59 | ecallt r0 60 | 61 | ldw r0, r4[3] // argv[argc] = null 62 | ldc r6, 8 63 | ecallt r0 64 | 65 | ldc r0, 0 66 | retsp 1 67 | 68 | .section .dp.data, "awd", @progbits 69 | .align 4 70 | _buffer: 71 | .space 400 72 | _buffer_end: 73 | 74 | .align 4 75 | _arg1: 76 | .asciiz "hello" 77 | 78 | .align 4 79 | _arg2: 80 | .asciiz "world" 81 | -------------------------------------------------------------------------------- /test/Interrupts/interrupt.S: -------------------------------------------------------------------------------- 1 | //RUN: xcc -O2 %s -x xc %s -target=XK-1A -o %t1.xe 2 | //RUN: %sim %t1.xe 3 | //RUN: xcc -O2 %s -x xc %s -target=XCORE-200-EXPLORER -mno-dual-issue -o %t1.xe 4 | //RUN: %sim %t1.xe 5 | #ifdef __XC__ 6 | #include 7 | 8 | void source(streaming chanend c) 9 | { 10 | while (1) 11 | c <: 0; 12 | } 13 | 14 | void sink(streaming chanend c) 15 | { 16 | for (unsigned i = 0; i < 100; i++) 17 | c :> int; 18 | exit(0); 19 | } 20 | 21 | 22 | void buffer(int buf[], unsigned bufsize_log2, streaming chanend a, 23 | streaming chanend b); 24 | 25 | #define SIZE_LOG_2 5 26 | 27 | int main() 28 | { 29 | streaming chan a, b; 30 | int array[1 << SIZE_LOG_2]; 31 | par { 32 | source(a); 33 | buffer(array, SIZE_LOG_2, a, b); 34 | sink(b); 35 | } 36 | return 0; 37 | } 38 | #else 39 | #include 40 | 41 | //r0 - buf 42 | //r1 - mask 43 | //r2 - inChan 44 | //r3 - outChan 45 | //r4 - read 46 | //r5 - write 47 | //r6 - nextWrite 48 | //r10 - tmp1 49 | //r11 - tmp2 50 | 51 | .align 4 52 | interrupt: 53 | in r11, res[r2] 54 | stw r11, r0[r5] 55 | mov r5, r6 56 | add r6, r5, 1 57 | and r6, r6, r1 58 | eq r11, r4, r6 59 | eet r11, res[r2] 60 | kret 61 | 62 | .globl buffer 63 | .align 4 64 | buffer: 65 | mkmsk r1, r1 66 | ldc r4, 0 67 | ldc r5, 0 68 | ldc r6, 1 69 | ldap r11, interrupt 70 | setv res[r2], r11 71 | setc res[r2], XS1_SETC_IE_MODE_INTERRUPT 72 | setsr XS1_SR_IEBLE_SET(0, 1) 73 | 74 | input: 75 | in r11, res[r2] 76 | stw r11, r0[r5] 77 | mov r5, r6 78 | add r6, r5, 1 79 | and r6, r6, r1 80 | 81 | output: 82 | add r11, r4, 1 83 | ldw r10, r0[r4] 84 | and r4, r11, r1 85 | eeu res[r2] 86 | out res[r3], r10 87 | edu res[r2] 88 | eq r10, r4, r5 89 | bf r10, output 90 | bu input 91 | .globl buffer.nstackwords 92 | .set buffer.nstackwords, 0 93 | #endif 94 | -------------------------------------------------------------------------------- /test/Exceptions/arithmetic.S: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A %s %exception_expect -o %t1.xe 2 | // RUN: %sim %t1.xe 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s %exception_expect -o %t1.xe 4 | // RUN: %sim %t1.xe 5 | #include 6 | 7 | .text 8 | .globl main 9 | .align 2 10 | main: 11 | entsp 1 12 | // Unsigned operations. 13 | // 7 / 0 14 | ldc r0, 7 15 | ldc r1, 0 16 | bl exception_expect 17 | ldc r1, 10 18 | ldc r11, 0 19 | divu r0, r1, r11 20 | 21 | bl exception_check 22 | // 7 % 0 23 | ldc r0, 7 24 | ldc r1, 0 25 | bl exception_expect 26 | ldc r1, 10 27 | ldc r11, 0 28 | remu r0, r1, r11 29 | 30 | bl exception_check 31 | // 0x000000005 / 0 32 | ldc r0, 7 33 | ldc r1, 0 34 | bl exception_expect 35 | ldc r2, 0 36 | ldc r3, 5 37 | ldc r11, 0 38 | ldivu r0, r1, r2, r3, r11 39 | 40 | bl exception_check 41 | // 0x700000005 / 0x7 42 | ldc r0, 7 43 | ldc r1, 0 44 | bl exception_expect 45 | ldc r2, 7 46 | ldc r3, 5 47 | ldc r11, 7 48 | ldivu r0, r1, r2, r3, r11 49 | 50 | // Signed operations. 51 | 52 | // 7 / 0 53 | ldc r0, 7 54 | ldc r1, 0 55 | bl exception_expect 56 | ldc r1, 10 57 | ldc r11, 0 58 | divs r0, r1, r11 59 | bl exception_check 60 | 61 | // MIN_INT / -1 62 | ldc r0, 7 63 | ldc r1, 0 64 | bl exception_expect 65 | .section .cp.rodata, "ac", @progbits 66 | .align 4 67 | const1: 68 | .word 0x80000000 69 | .text 70 | ldw r1, cp[const1] 71 | mkmsk r11, 32 72 | divs r0, r1, r11 73 | bl exception_check 74 | 75 | // 7 % 0 76 | ldc r0, 7 77 | ldc r1, 0 78 | bl exception_expect 79 | ldc r1, 10 80 | ldc r11, 0 81 | rems r0, r1, r11 82 | bl exception_check 83 | 84 | // MIN_INT % -1 85 | ldc r0, 7 86 | ldc r1, 0 87 | bl exception_expect 88 | ldw r1, cp[const1] 89 | mkmsk r11, 32 90 | rems r0, r1, r11 91 | bl exception_check 92 | 93 | ldc r0, 0 94 | retsp 1 95 | -------------------------------------------------------------------------------- /test/Resources/Ports/events.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XK-1A -O2 %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback 0x10000 0x10300 --loopback 0x10200 0x10100 3 | // RUN: xcc -target=XCORE-200-EXPLORER -O2 %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback 0x10000 0x10300 --loopback 0x10200 0x10100 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | struct port_pair { 11 | port first; 12 | port second; 13 | }; 14 | 15 | struct port_pair a = { 16 | XS1_PORT_1A, 17 | XS1_PORT_1B 18 | }; 19 | 20 | struct port_pair b = { 21 | XS1_PORT_1C, 22 | XS1_PORT_1D 23 | }; 24 | 25 | unsigned char getByte() 26 | { 27 | return 0x57; 28 | } 29 | 30 | void sender(struct port_pair &p) { 31 | timer t; 32 | unsigned time; 33 | unsigned char value; 34 | unsigned first_value = 0, second_value = 0; 35 | value = getByte(); 36 | t :> time; 37 | for (unsigned i = 0; i < 8; i++) { 38 | t when timerafter(time+=100) :> void; 39 | if (value & 1) { 40 | second_value = !second_value; 41 | p.second <: second_value; 42 | } else { 43 | first_value = !first_value; 44 | p.first <: first_value; 45 | } 46 | value >>= 1; 47 | } 48 | } 49 | 50 | void putByte(unsigned char b) 51 | { 52 | if (b != 0x57) 53 | exit(1); 54 | exit(0); 55 | } 56 | 57 | void receiver(struct port_pair &p) 58 | { 59 | // Transition on A == 0 60 | // Transition on B == 1 61 | unsigned first_val = 0, second_val = 0; 62 | unsigned char value; 63 | for (unsigned i = 0; i < 8; i++) { 64 | select { 65 | case p.first when pinsneq(first_val) :> first_val: 66 | value >>= 1; 67 | break; 68 | case p.second when pinsneq(second_val) :> second_val: 69 | value >>= 1; 70 | value |= (1 << 7); 71 | break; 72 | } 73 | } 74 | putByte(value); 75 | } 76 | 77 | int main() 78 | { 79 | a.first <: 0; 80 | a.second <: 0; 81 | par { 82 | sender(a); 83 | receiver(b); 84 | } 85 | return 0; 86 | } 87 | -------------------------------------------------------------------------------- /test/Resources/Ports/setpsc_output.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -O2 -target=XK-1A %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback XS1_PORT_1A XS1_PORT_1F --loopback XS1_PORT_1B XS1_PORT_1E --loopback XS1_PORT_1C XS1_PORT_1G --loopback XS1_PORT_1D XS1_PORT_1H 3 | // RUN: xcc -O2 -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback XS1_PORT_1A XS1_PORT_1F --loopback XS1_PORT_1B XS1_PORT_1E --loopback XS1_PORT_1C XS1_PORT_1G --loopback XS1_PORT_1D XS1_PORT_1H 5 | 6 | #include 7 | 8 | port p_readyin = XS1_PORT_1A; 9 | port p_readyout = XS1_PORT_1B; 10 | port p_clk_port = XS1_PORT_1C; 11 | in buffered port:8 p = XS1_PORT_1D; 12 | clock p_clk = XS1_CLKBLK_1; 13 | 14 | port q_readyin = XS1_PORT_1E; 15 | port q_readyout = XS1_PORT_1F; 16 | port q_clk_port = XS1_PORT_1G; 17 | out buffered port:8 q = XS1_PORT_1H; 18 | clock q_clk = XS1_CLKBLK_2; 19 | 20 | clock clk_gen = XS1_CLKBLK_3; 21 | 22 | #define MAGIC_VALUE 0x2e 23 | 24 | // Defeat optimizers. 25 | int identity(int x) 26 | { 27 | asm("mov %0, %1" : "=r"(x) : "r"(x)); 28 | return x; 29 | } 30 | 31 | int main() 32 | { 33 | int received = 0; 34 | /* Configure generated clock */ 35 | configure_clock_ref(clk_gen, 20); 36 | 37 | /* Configure p_clk */ 38 | configure_port_clock_output(p_clk_port, clk_gen); 39 | 40 | /* Configure p */ 41 | configure_clock_src(p_clk, p_clk_port); 42 | configure_in_port_handshake(p, p_readyin, p_readyout, p_clk); 43 | 44 | /* Configure q */ 45 | configure_clock_src(q_clk, q_clk_port); 46 | configure_out_port_handshake(q, q_readyin, q_readyout, q_clk, 0); 47 | 48 | /* Start */ 49 | start_clock(p_clk); 50 | start_clock(q_clk); 51 | start_clock(clk_gen); 52 | 53 | /* Transfer data */ 54 | partout(q, identity(3), MAGIC_VALUE); 55 | partout(q, identity(5), MAGIC_VALUE >> 3); 56 | 57 | p :> received; 58 | if (received != MAGIC_VALUE) 59 | return 1; 60 | 61 | return 0; 62 | } 63 | -------------------------------------------------------------------------------- /test/Resources/Ports/multicore.xc: -------------------------------------------------------------------------------- 1 | // RUN: xcc -target=XS1-L16A-128-QF124-C10 %s -o %t1.xe 2 | // RUN: axe %t1.xe --loopback tile[0]:XS1_PORT_1A tile[1]:XS1_PORT_1A 3 | // RUN: xcc -target=XCORE-200-EXPLORER %s -o %t1.xe 4 | // RUN: axe %t1.xe --loopback tile[0]:XS1_PORT_1A tile[1]:XS1_PORT_1A 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #define BIT_RATE 115200 11 | #define BIT_TIME 100000000 / BIT_RATE 12 | 13 | out port TXD = on tile[0] : XS1_PORT_1A; 14 | in port RXD = on tile[1] : XS1_PORT_1A; 15 | 16 | unsigned char getByte() 17 | { 18 | return 0xa3; 19 | } 20 | 21 | void transmitter (out port TXD) { 22 | unsigned byte, time; 23 | timer t; 24 | /* get next byte to transmit */ 25 | byte = getByte(); 26 | t :> time ; 27 | /* output start bit */ 28 | TXD <: 0; 29 | time += BIT_TIME ; 30 | t when timerafter(time) :> void; 31 | /* output data bits */ 32 | for (int i = 0; i < 8; i++) { 33 | TXD <: >> byte; 34 | time += BIT_TIME; 35 | t when timerafter(time) :> void; 36 | } 37 | /* output stop bit */ 38 | TXD <: 1; 39 | time += BIT_TIME ; 40 | t when timerafter(time) :> void; 41 | } 42 | 43 | void putByte(unsigned char b) 44 | { 45 | if (b != 0xa3) 46 | exit(1); 47 | exit(0); 48 | } 49 | 50 | void receiver(in port RXD) { 51 | unsigned byte, time; 52 | timer t; 53 | /* wait for start bit */ 54 | RXD when pinseq(0) :> void; 55 | t :> time; 56 | time += BIT_TIME / 2; 57 | /* input data bits */ 58 | for (int i = 0; i < 8; i++) { 59 | time += BIT_TIME; 60 | t when timerafter(time) :> void; 61 | RXD :> >> byte; 62 | } 63 | /* input stop bit */ 64 | time += BIT_TIME; 65 | t when timerafter(time) :> void; 66 | RXD :> void; 67 | putByte(byte >> 24); 68 | } 69 | 70 | 71 | int main() 72 | { 73 | par { 74 | on tile[0] : transmitter(TXD); 75 | on tile[1] : receiver(RXD); 76 | } 77 | return 0; 78 | } 79 | -------------------------------------------------------------------------------- /thirdparty/lit/setup.py: -------------------------------------------------------------------------------- 1 | import lit 2 | 3 | # FIXME: Support distutils? 4 | from setuptools import setup, find_packages 5 | setup( 6 | name = "Lit", 7 | version = lit.__version__, 8 | 9 | author = lit.__author__, 10 | author_email = lit.__email__, 11 | url = 'http://llvm.org', 12 | license = 'BSD', 13 | 14 | description = "A Software Testing Tool", 15 | keywords = 'test C++ automatic discovery', 16 | long_description = """\ 17 | Lit 18 | +++ 19 | 20 | About 21 | ===== 22 | 23 | Lit is a portable tool for executing LLVM and Clang style test suites, 24 | summarizing their results, and providing indication of failures. Lit is designed 25 | to be a lightweight testing tool with as simple a user interface as possible. 26 | 27 | 28 | Features 29 | ======== 30 | 31 | * Portable! 32 | * Flexible test discovery. 33 | * Parallel test execution. 34 | * Support for multiple test formats and test suite designs. 35 | 36 | 37 | Documentation 38 | ============= 39 | 40 | The offical Lit documentation is in the man page, available online in the `LLVM 41 | Command Guide http://llvm.org/cmds/lit.html`_. 42 | 43 | 44 | Source 45 | ====== 46 | 47 | The Lit source is available as part of LLVM, in the `LLVM SVN repository 48 | 5 | 6 | #include "XMLUtils.h" 7 | #include 8 | #include 9 | #include 10 | 11 | xmlNode *axe::findChild(xmlNode *node, const char *name) 12 | { 13 | for (xmlNode *child = node->children; child; child = child->next) { 14 | if (child->type != XML_ELEMENT_NODE) 15 | continue; 16 | if (std::strcmp(name, (char*)child->name) == 0) 17 | return child; 18 | } 19 | return 0; 20 | } 21 | 22 | xmlAttr *axe::findAttribute(xmlNode *node, const char *name) 23 | { 24 | for (xmlAttr *child = node->properties; child; child = child->next) { 25 | if (child->type != XML_ATTRIBUTE_NODE) 26 | continue; 27 | if (std::strcmp(name, (char*)child->name) == 0) 28 | return child; 29 | } 30 | return 0; 31 | } 32 | 33 | xmlDoc *axe:: 34 | applyXSLTTransform(xmlDoc *doc, const char *transformData) 35 | { 36 | xmlDoc *transformDoc = 37 | xmlReadDoc(BAD_CAST transformData, "XNTransform.xslt", NULL, 0); 38 | xsltStylesheetPtr stylesheet = xsltParseStylesheetDoc(transformDoc); 39 | xmlDoc *newDoc = xsltApplyStylesheet(stylesheet, doc, NULL); 40 | xsltFreeStylesheet(stylesheet); 41 | return newDoc; 42 | } 43 | 44 | bool axe:: 45 | checkDocAgainstSchema(xmlDoc *doc, const char *schemaData, size_t schemaSize) 46 | { 47 | xmlRelaxNGParserCtxtPtr schemaContext = 48 | xmlRelaxNGNewMemParserCtxt(schemaData, schemaSize); 49 | xmlRelaxNGPtr schema = xmlRelaxNGParse(schemaContext); 50 | xmlRelaxNGValidCtxtPtr validationContext = 51 | xmlRelaxNGNewValidCtxt(schema); 52 | bool isValid = xmlRelaxNGValidateDoc(validationContext, doc) == 0; 53 | xmlRelaxNGFreeValidCtxt(validationContext); 54 | xmlRelaxNGFree(schema); 55 | xmlRelaxNGFreeParserCtxt(schemaContext); 56 | return isValid; 57 | } 58 | -------------------------------------------------------------------------------- /NETWORK.rst: -------------------------------------------------------------------------------- 1 | Network support 2 | ............... 3 | 4 | AXE can emulate an ethernet PHY supporting the Media Independent Interface 5 | (MII). The emulated PHY passes ethernet frames to and from a virtual TAP 6 | networking device on the host. Usually root privileges are required to create 7 | and configure the TAP device. The steps needed to configure the TAP device 8 | depend on the operating system you are using. 9 | 10 | An ethernet PHY instance is created using the --ethernet-phy option. The 11 | following port arguments are mandatory regardless of the operating system: 12 | 13 | * tx_clk= 14 | * tx_en= 15 | * txd= 16 | * rx_clk= 17 | * rx_dv= 18 | * rx_er= 19 | * rxd= 20 | 21 | Windows 22 | ======= 23 | 24 | Not yet supported. 25 | 26 | OS X 27 | ==== 28 | OS X does not ship with a TUN/TAP driver. OS X TUN/TAP drivers can be 29 | installed from http://tuntaposx.sourceforge.net. 30 | 31 | When run with no additional arguments AXE will try and open the first 32 | available TAP device, starting with tap0. You can specify a device to use 33 | with the -ifname= option. The network interface is created when the 34 | device is opened and it can be configured using ifconfig. For example:: 35 | 36 | ifconfig tap0 up 37 | 38 | Linux 39 | ===== 40 | Modern versions of the Linux kernel come with a TUN/TAP driver. 41 | 42 | When run with no additional arguments AXE will try and create a new TAP 43 | device. You can specify a device to use with the -ifname= option. This 44 | can be used to open an existing TAP device created by, for example, 45 | tunctl (from UML utilities) or openvpn --mktun (from OpenVPN). 46 | 47 | The TAP interface can be configured using ifconfig. For example:: 48 | 49 | ifconfig tap0 up 50 | 51 | It is also possible to add the TAP interface to an ethernet bridge. This can 52 | be used to connect two instances of AXE or to allow AXE to communicate with 53 | devices on a physical network. Details of setting up ethernet bridges are 54 | beyond the scope of this document. 55 | -------------------------------------------------------------------------------- /lib/Tracer.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011-2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Tracer.h" 7 | 8 | using namespace axe; 9 | 10 | Tracer::~Tracer() 11 | { 12 | } 13 | 14 | void Tracer::attach(const SystemState &systemState) 15 | { 16 | } 17 | 18 | void Tracer::instructionBegin(const Thread &t) 19 | { 20 | } 21 | 22 | void Tracer::regWrite(Register::Reg reg, uint32_t value) 23 | { 24 | } 25 | 26 | void Tracer::instructionEnd() 27 | { 28 | } 29 | 30 | void Tracer::SSwitchRead(const Node &node, uint32_t retAddress, 31 | uint16_t regNum) 32 | { 33 | } 34 | 35 | void Tracer::SSwitchWrite(const Node &node, uint32_t retAddress, 36 | uint16_t regNum, uint32_t value) 37 | { 38 | } 39 | 40 | void Tracer::SSwitchNack(const Node &node, uint32_t dest) 41 | { 42 | } 43 | 44 | void Tracer::SSwitchAck(const Node &node, uint32_t dest) 45 | { 46 | } 47 | 48 | void Tracer::SSwitchAck(const Node &node, uint32_t data, uint32_t dest) 49 | { 50 | } 51 | 52 | void Tracer::exception(const Thread &t, uint32_t et, uint32_t ed, 53 | uint32_t sed, uint32_t ssr, uint32_t spc) 54 | { 55 | } 56 | 57 | void Tracer::event(const Thread &t, const EventableResource &res, uint32_t pc, 58 | uint32_t ev) 59 | { 60 | } 61 | 62 | void Tracer::interrupt(const Thread &t, const EventableResource &res, 63 | uint32_t pc, uint32_t ssr, uint32_t spc, uint32_t sed, 64 | uint32_t ed) 65 | { 66 | } 67 | 68 | void Tracer::syscall(const Thread &t, const std::string &s) 69 | { 70 | } 71 | 72 | void Tracer::syscall(const Thread &t, const std::string &s, uint32_t op0) 73 | { 74 | } 75 | 76 | void Tracer::timeout(const SystemState &system, ticks_t time) 77 | { 78 | } 79 | 80 | void Tracer::noRunnableThreads(const SystemState &system) 81 | { 82 | } 83 | -------------------------------------------------------------------------------- /lib/StatsTracer.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "StatsTracer.h" 7 | #include "llvm/Support/raw_ostream.h" 8 | 9 | using namespace axe; 10 | 11 | StatsTracer::StatsTracer() : 12 | numInstructions(0), 13 | numExceptions(0), 14 | numEvents(0), 15 | numInterrupts(0), 16 | numSyscalls(0) 17 | { 18 | } 19 | 20 | StatsTracer::~StatsTracer() 21 | { 22 | display(); 23 | } 24 | 25 | void StatsTracer::display() 26 | { 27 | llvm::raw_ostream &out = llvm::outs(); 28 | out << "Statistics:\n"; 29 | out << "-----------\n"; 30 | out << "Instructions executed: " << numInstructions << '\n'; 31 | // TODO Real time elapsed: 32 | // TODO Simulator MIPs: 33 | out << "Number of events: " << numEvents << '\n'; 34 | out << "Number of interrupts " << numInterrupts << '\n'; 35 | out << "Number of exceptions: " << numExceptions << '\n'; 36 | out << "Number of system calls: " << numSyscalls << '\n'; 37 | } 38 | 39 | void StatsTracer::instructionBegin(const Thread &t) 40 | { 41 | ++numInstructions; 42 | } 43 | 44 | void StatsTracer::exception(const Thread &t, uint32_t et, uint32_t ed, 45 | uint32_t sed, uint32_t ssr, uint32_t spc) 46 | { 47 | ++numExceptions; 48 | } 49 | 50 | void StatsTracer::event(const Thread &t, const EventableResource &res, uint32_t pc, 51 | uint32_t ev) 52 | { 53 | ++numEvents; 54 | } 55 | 56 | void StatsTracer::interrupt(const Thread &t, const EventableResource &res, uint32_t pc, 57 | uint32_t ssr, uint32_t spc, uint32_t sed, 58 | uint32_t ed) 59 | { 60 | ++numInterrupts; 61 | } 62 | 63 | void StatsTracer::syscall(const Thread &t, const std::string &s) 64 | { 65 | ++numSyscalls; 66 | } 67 | 68 | void StatsTracer::syscall(const Thread &t, const std::string &s, uint32_t op0) 69 | { 70 | ++numSyscalls; 71 | } 72 | -------------------------------------------------------------------------------- /lib/SSwitch.h: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #ifndef _SSwitch_h_ 7 | #define _SSwitch_h_ 8 | 9 | #include "Token.h" 10 | #include "ChanEndpoint.h" 11 | #include "SSwitchCtrlRegs.h" 12 | 13 | namespace axe { 14 | 15 | class Node; 16 | 17 | class SSwitch : public ChanEndpoint { 18 | private: 19 | struct Request { 20 | bool write; 21 | uint16_t returnNode; 22 | uint8_t returnNum; 23 | uint32_t regNum; 24 | uint32_t data; 25 | }; 26 | Node *parent; 27 | SSwitchCtrlRegs regs; 28 | /// Length of a write request (excluding CT_END). 29 | static const unsigned writeRequestLength = 1 + 3 + 2 + 4; 30 | /// Length of a read request (excluding CT_END). 31 | static const unsigned readRequestLength = 1 + 3 + 2; 32 | /// Number of tokens in the buffer. 33 | unsigned recievedTokens; 34 | Token buf[writeRequestLength]; 35 | bool junkIncomingTokens; 36 | /// Are we in the middle of sending a response? 37 | bool sendingResponse; 38 | unsigned sentTokens; 39 | /// Length of response (including CT_END). 40 | unsigned responseLength; 41 | bool parseRequest(ticks_t time, Request &request) const; 42 | void handleRequest(ticks_t time, const Request &request); 43 | public: 44 | SSwitch(Node *parent); 45 | void initRegisters() { regs.initRegisters(); } 46 | void notifyDestClaimed(ticks_t time) override; 47 | 48 | void notifyDestCanAcceptTokens(ticks_t time, unsigned tokens) override; 49 | 50 | bool canAcceptToken() override; 51 | bool canAcceptTokens(unsigned tokens) override; 52 | 53 | void receiveDataToken(ticks_t time, uint8_t value) override; 54 | 55 | void receiveDataTokens(ticks_t time, uint8_t *values, unsigned num) override; 56 | 57 | void receiveCtrlToken(ticks_t time, uint8_t value) override; 58 | }; 59 | 60 | } // End axe namespace 61 | 62 | #endif //_SSwitch_h_ 63 | 64 | -------------------------------------------------------------------------------- /lib/Synchroniser.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2011, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "Synchroniser.h" 7 | #include "Core.h" 8 | 9 | using namespace axe; 10 | 11 | ticks_t Synchroniser::MaxThreadTime() const 12 | { 13 | ticks_t time = threads[0]->time; 14 | for (unsigned i = 1; i < NumThreads; i++) { 15 | if (threads[i]->time > time) 16 | time = threads[i]->time; 17 | } 18 | return time; 19 | } 20 | 21 | Synchroniser::SyncResult Synchroniser:: 22 | sync(Thread &thread, bool isMaster) 23 | { 24 | if (getNumPaused() + 1 < getNumThreads()) { 25 | // Pause the current thread 26 | NumPaused++; 27 | if (!isMaster) 28 | thread.setSSync(true); 29 | return SYNC_DESCHEDULE; 30 | } 31 | // Wakeup / kill threads 32 | ticks_t newTime = MaxThreadTime(); 33 | NumPaused = 0; 34 | if (!join) { 35 | for (unsigned i = 0; i < NumThreads; i++) { 36 | threads[i]->time = newTime; 37 | if (threads[i] != &thread) { 38 | if (i > 0) 39 | threads[i]->setSSync(false); 40 | threads[i]->pc++; 41 | threads[i]->schedule(); 42 | } 43 | } 44 | return SYNC_CONTINUE; 45 | } 46 | SyncResult result; 47 | threads[0]->time = newTime; 48 | if (isMaster) { 49 | result = SYNC_CONTINUE; 50 | for (unsigned i = 1; i < NumThreads; i++) { 51 | threads[i]->free(); 52 | } 53 | } else { 54 | master().schedule(); 55 | result = SYNC_KILL; 56 | for (unsigned i = 1; i < NumThreads; i++) { 57 | if (threads[i] != &thread) { 58 | threads[i]->free(); 59 | } 60 | } 61 | } 62 | join = false; 63 | NumThreads = 1; 64 | return result; 65 | } 66 | 67 | Synchroniser::SyncResult Synchroniser:: 68 | mjoin(Thread &thread) 69 | { 70 | join = true; 71 | return sync(thread, true); 72 | } 73 | 74 | void Synchroniser::cancel() 75 | { 76 | NumPaused--; 77 | } 78 | -------------------------------------------------------------------------------- /lib/PortSplitter.cpp: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2012, Richard Osborne, All rights reserved 2 | // This software is freely distributable under a derivative of the 3 | // University of Illinois/NCSA Open Source License posted in 4 | // LICENSE.txt and at 5 | 6 | #include "PortSplitter.h" 7 | #include "PortHandleClockMixin.h" 8 | #include "BitManip.h" 9 | #include 10 | 11 | using namespace axe; 12 | 13 | class axe::PortSplitterSlice final : public PortHandleClockMixin { 14 | PortSplitter *parent; 15 | unsigned shift; 16 | uint32_t mask; 17 | public: 18 | PortSplitterSlice(PortSplitter *p, RunnableQueue &scheduler, unsigned s, 19 | uint32_t m) : 20 | PortHandleClockMixin(scheduler), 21 | parent(p), 22 | shift(s), 23 | mask(m) {} 24 | void seePinsValueChange(uint32_t value, ticks_t time); 25 | }; 26 | 27 | void PortSplitterSlice::seePinsValueChange(uint32_t value, ticks_t time) 28 | { 29 | parent->seePinsValueChange(value, time, shift, mask); 30 | } 31 | 32 | PortSplitter::PortSplitter(RunnableQueue &s, PortInterface *p) : 33 | scheduler(s), 34 | port(p), 35 | value(0) 36 | { 37 | } 38 | 39 | PortSplitter::~PortSplitter() 40 | { 41 | for (auto &entry : slices) { 42 | delete entry.second; 43 | } 44 | } 45 | 46 | PortInterface *PortSplitter:: 47 | getInterface(unsigned beginOffset, unsigned endOffset) 48 | { 49 | PortSplitterSlice *&slice = slices[std::make_pair(beginOffset, endOffset)]; 50 | if (!slice) { 51 | unsigned shift = beginOffset; 52 | uint32_t mask = makeMask(endOffset - beginOffset) << beginOffset; 53 | slice = new PortSplitterSlice(this, scheduler, shift, mask); 54 | } 55 | return slice; 56 | } 57 | 58 | void PortSplitter:: 59 | seePinsValueChange(uint32_t sliceValue, ticks_t time, unsigned shift, 60 | uint32_t mask) 61 | { 62 | uint32_t newValue = value; 63 | newValue ^= ((sliceValue << shift) ^ newValue) & mask; 64 | if (newValue != value) { 65 | value = newValue; 66 | port->seePinsChange(Signal(value), time); 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /thirdparty/lit/LICENSE.TXT: -------------------------------------------------------------------------------- 1 | ============================================================================== 2 | LLVM Release License 3 | ============================================================================== 4 | University of Illinois/NCSA 5 | Open Source License 6 | 7 | Copyright (c) 2003-2010 University of Illinois at Urbana-Champaign. 8 | All rights reserved. 9 | 10 | Developed by: 11 | 12 | LLVM Team 13 | 14 | University of Illinois at Urbana-Champaign 15 | 16 | http://llvm.org 17 | 18 | Permission is hereby granted, free of charge, to any person obtaining a copy of 19 | this software and associated documentation files (the "Software"), to deal with 20 | the Software without restriction, including without limitation the rights to 21 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies 22 | of the Software, and to permit persons to whom the Software is furnished to do 23 | so, subject to the following conditions: 24 | 25 | * Redistributions of source code must retain the above copyright notice, 26 | this list of conditions and the following disclaimers. 27 | 28 | * Redistributions in binary form must reproduce the above copyright notice, 29 | this list of conditions and the following disclaimers in the 30 | documentation and/or other materials provided with the distribution. 31 | 32 | * Neither the names of the LLVM Team, University of Illinois at 33 | Urbana-Champaign, nor the names of its contributors may be used to 34 | endorse or promote products derived from this Software without specific 35 | prior written permission. 36 | 37 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 38 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 39 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 40 | CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 41 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 42 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS WITH THE 43 | SOFTWARE. 44 | -------------------------------------------------------------------------------- /cmake/Modules/FindSDL2.cmake: -------------------------------------------------------------------------------- 1 | # Locate SDL2 2 | # This module defines 3 | # SDL2_FOUND - System has SDL2 4 | # SDL2_CONFIG_EXECUTABLE - The sdl2-config executable 5 | # SDL2_INCLUDE_DIRS - SDL2 include directories 6 | # SDL2_DEFINITIONS - SDL2 compiler definitions 7 | # SDL2_LIBRARIES - Libraries needed to link against SDL2 8 | 9 | find_program(SDL2_CONFIG_EXECUTABLE 10 | NAMES sdl2-config 11 | DOC "sdl2-config executable") 12 | 13 | include(FindPackageHandleStandardArgs) 14 | # Sets SDL2_FOUND 15 | find_package_handle_standard_args( 16 | SDL2 DEFAULT_MSG SDL2_CONFIG_EXECUTABLE) 17 | 18 | if (SDL2_FOUND) 19 | if (MINGW AND ${CMAKE_GENERATOR} STREQUAL "MSYS Makefiles") 20 | execute_process( 21 | COMMAND sh -c "${SDL2_CONFIG_EXECUTABLE} --cflags" 22 | OUTPUT_VARIABLE SDL2_CFLAGS 23 | OUTPUT_STRIP_TRAILING_WHITESPACE 24 | ) 25 | 26 | execute_process( 27 | COMMAND sh -c "${SDL2_CONFIG_EXECUTABLE} --libs" 28 | OUTPUT_VARIABLE SDL2_LIBRARIES 29 | OUTPUT_STRIP_TRAILING_WHITESPACE 30 | ) 31 | else() 32 | execute_process( 33 | COMMAND ${SDL2_CONFIG_EXECUTABLE} --cflags 34 | OUTPUT_VARIABLE SDL2_CFLAGS 35 | OUTPUT_STRIP_TRAILING_WHITESPACE 36 | ) 37 | 38 | execute_process( 39 | COMMAND ${SDL2_CONFIG_EXECUTABLE} --libs 40 | OUTPUT_VARIABLE SDL2_LIBRARIES 41 | OUTPUT_STRIP_TRAILING_WHITESPACE 42 | ) 43 | endif() 44 | 45 | # Workaround SDL bug 2029 (-XCClinker isn't recognised by MinGW gcc). 46 | if (MINGW) 47 | STRING(REGEX REPLACE "-XCClinker " "" SDL2_LIBRARIES ${SDL2_LIBRARIES}) 48 | endif() 49 | 50 | # Extract include directories / defines 51 | string(REPLACE " " ";" SDL2_CFLAGS_LIST ${SDL2_CFLAGS}) 52 | foreach(FLAG ${SDL2_CFLAGS_LIST}) 53 | if(${FLAG} MATCHES "^-I") 54 | STRING(REGEX REPLACE "^-I" "" FLAG ${FLAG}) 55 | list(APPEND SDL2_INCLUDE_DIRS ${FLAG}) 56 | elseif(${FLAG} MATCHES "^-D") 57 | STRING(REGEX REPLACE "^-D" "" FLAG ${FLAG}) 58 | list(APPEND SDL2_DEFINITIONS ${FLAG}) 59 | endif() 60 | endforeach() 61 | endif() 62 | 63 | mark_as_advanced(SDL2_CONFIG_EXECUTABLE) 64 | --------------------------------------------------------------------------------