aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Makefile9
-rw-r--r--flake.nix14
-rw-r--r--src/Top.bs54
-rw-r--r--src/UART.bs101
-rw-r--r--src/Util.bs7
5 files changed, 130 insertions, 55 deletions
diff --git a/Makefile b/Makefile
index 574b9b7..5157357 100644
--- a/Makefile
+++ b/Makefile
@@ -1,13 +1,12 @@
BSC_COMP_FLAGS = -aggressive-conditions -bdir tmp -check-assert -keep-fires \
- -p src:$(BSC_CONTRIB)/Libraries/FPGA/Misc:+ -vdir tmp
+ -p src:+ -vdir tmp
BSC_LINK_FLAGS = -keep-fires
-BSC_SOURCES = Counter.v SizedFIFO.v
TOPFILE = Top
TOPMODULE = mkTop
SRCS = $(shell find src -name '*.bs')
all: tmp/$(TOPMODULE).bin
-clean: clean.sh
+clean:
@git status --porcelain=v1 --ignored -z \
| grep -z '^!!' \
| xargs -0 awk 'BEGIN { for(i = 1; i < ARGC; i++) printf "%s%c", substr(ARGV[i], 4), 0; }' \
@@ -17,12 +16,12 @@ flash: tmp/$(TOPMODULE).bin
.PHONY: all clean flash
tmp/%.bin: tmp/%.asc
- # icetime -d up5k -c 12 $<
+ icetime -d up5k -c 12 $<
icepack $< $@
tmp/%.asc: tmp/%.json src/icebreaker.pcf
nextpnr-ice40 -ql tmp/$*.nplog --up5k --package sg48 --freq 12 \
--asc $@ --pcf src/icebreaker.pcf --json $<
-tmp/$(TOPMODULE).json: tmp/$(TOPMODULE).v $(addprefix $(BSC)/lib/Verilog/,$(BSC_SOURCES))
+tmp/$(TOPMODULE).json: tmp/$(TOPMODULE).v
yosys -ql tmp/$(TOPMODULE).yslog -p 'synth_ice40 -top mkTop -json $@' $^
tmp/$(TOPMODULE).v: tmp/$(TOPFILE).bo
bsc -g $(TOPMODULE) -verilog $(BSC_COMP_FLAGS) src/$(TOPFILE).bs
diff --git a/flake.nix b/flake.nix
index 0dd1743..ef36aef 100644
--- a/flake.nix
+++ b/flake.nix
@@ -2,15 +2,7 @@
inputs.nixpkgs.url = "github:NixOS/nixpkgs";
outputs = { self, flake-utils, nixpkgs }:
flake-utils.lib.eachDefaultSystem (system:
- let
- pkgs = nixpkgs.legacyPackages.${system};
- bsc-contrib = pkgs.fetchFromGitHub {
- name = "bsc-contrib-src";
- owner = "B-Lang-org";
- repo = "bsc-contrib";
- rev = "fc26b91c8add9660204c4311dcc60d223ed23ea5";
- hash = "sha256-7H+R7QwcyskrXGO51zZuuyIwZZROc25gJy9nqg/I6lM=";
- };
+ let pkgs = nixpkgs.legacyPackages.${system};
in rec {
devShells.default = pkgs.mkShell {
inputsFrom = builtins.attrValues packages;
@@ -22,10 +14,6 @@
pkgs.picocom
pkgs.yosys
];
- env = {
- BSC = pkgs.bluespec;
- BSC_CONTRIB = bsc-contrib;
- };
};
packages = { };
diff --git a/src/Top.bs b/src/Top.bs
index 61bdc86..2a056ac 100644
--- a/src/Top.bs
+++ b/src/Top.bs
@@ -1,7 +1,6 @@
package Top where
-import GetPut
-import RS232
+import UART
interface Top =
-- RS232
@@ -30,49 +29,30 @@ clockFreqHz = 12_000_000
mkTop :: Module Top
mkTop =
module
- let uartBaud :: Integer
- uartBaud = 115200
- uartDivider :: Integer
- uartDivider = clockFreqHz / uartBaud
- uart :: UART 8 <- mkUART 8 NONE STOP_1 (fromInteger uartDivider)
-
- clkState :: Reg (Bit 32) <- mkReg 0
- btn1State :: Reg (Bit 1) <- mkReg 0
- btn2State :: Reg (Bit 1) <- mkReg 0
- btn3State :: Reg (Bit 1) <- mkReg 0
- led4State :: Reg (Bit 1) <- mkReg 0
- led5State :: Reg (Bit 1) <- mkReg 0
-
- rules
- "echo": when (clkState == 0) ==> do
- led4State := led4State + 1
- uart.rx.put 0x7e
- "increment_clock": when True ==> do
- if clkState == fromInteger (clockFreqHz / 10) then do
- clkState := 0
- led5State := led5State + 1
- else
- clkState := clkState + 1
+ bitState :: Reg (Bit 1) <- mkReg 0
+ uart <- mkUART (clockFreqHz / 9600)
interface Top
-- RS232
- rx = uart.rs232.sin
- tx = uart.rs232.sout
+ rx bit = do
+ bitState := bit
+ uart.rxPin bit
+ tx = uart.txPin
-- Onboard LEDs
- ledR_N = 1
- ledG_N = 1
+ ledR_N = uart.txPin
+ ledG_N = bitState
-- RGB LED driver
ledRed_N = 1
ledGrn_N = 1
ledBlu_N = 1
-- LEDs and buttons (PMOD 2)
- led1 = btn1State
- led2 = btn2State
- led3 = btn3State
- led4 = led4State
- led5 = led5State
- btn1 x = btn1State := x
- btn2 x = btn2State := x
- btn3 x = btn3State := x
+ led1 = 0
+ led2 = 0
+ led3 = 0
+ led4 = 0
+ led5 = 0
+ btn1 _ = return ()
+ btn2 _ = return ()
+ btn3 _ = return ()
{-# verilog mkTop #-}
{-# properties mkTop = { RSTN = BTN_N } #-}
diff --git a/src/UART.bs b/src/UART.bs
new file mode 100644
index 0000000..f837949
--- /dev/null
+++ b/src/UART.bs
@@ -0,0 +1,101 @@
+package UART where
+
+import GetPut
+import Util
+
+interface Clock =
+ clk :: Bool
+
+defaultClock :: Clock
+defaultClock =
+ interface Clock
+ clk = True
+
+mkDivider :: Integer -> Clock -> Module Clock
+mkDivider divisor clockIn =
+ module
+ count <- mkReg 0
+
+ rules
+ "increment_divider": when clockIn.clk ==> do
+ if count == fromInteger divisor then do
+ count := 0
+ else
+ count := count + 1
+
+ interface Clock
+ clk = count == 0
+
+interface ShiftRegister =
+ get :: Get (Bit 1)
+ put :: Put (Bit 1)
+
+mkShiftRegister :: Module ShiftRegister
+mkShiftRegister =
+ module
+ reg :: Reg (Bit 8) <- mkReg 0
+
+ interface ShiftRegister
+ get = interface Get
+ get = return 0
+ put = interface Put
+ put bit = do
+ return ()
+
+-- An 8n1 UART.
+interface UART =
+ -- The RX pin.
+ rxPin :: Bit 1 -> Action
+ -- The TX pin.
+ txPin :: Bit 1
+
+ -- Reads a byte from the UART.
+ rxByte :: Get (Bit 8)
+ -- Writes a byte to the UART.
+ txByte :: Put (Bit 8)
+
+mkUART :: Integer -> Module UART
+mkUART baudDivisor =
+ module
+ baud <- mkDivider baudDivisor defaultClock
+
+ count :: Reg (Bit 4) <- mkReg 0
+ rules
+ "increment_count": when baud.clk ==> do
+ count := count + 1
+
+ let start = 0
+ d0 = 1
+ d1 = 0
+ d2 = 0
+ d3 = 0
+ d4 = 1
+ d5 = 0
+ d6 = 0
+ d7 = 0
+ stop = 1
+
+ interface UART
+ rxPin _bit = when_ baud.clk $ do
+ return () -- TODO
+ txPin = case count of
+ 0 -> start
+ 1 -> d0
+ 2 -> d1
+ 3 -> d2
+ 4 -> d3
+ 5 -> d4
+ 6 -> d5
+ 7 -> d6
+ 8 -> d7
+ 9 -> stop
+ _ -> 1
+
+ rxByte = interface Get
+ get = return 0 when False
+ txByte = interface Put
+ put _ = do
+ -- TODO
+ return ()
+
+-- vim: set ft=haskell :
diff --git a/src/Util.bs b/src/Util.bs
new file mode 100644
index 0000000..ab3074c
--- /dev/null
+++ b/src/Util.bs
@@ -0,0 +1,7 @@
+package Util where
+
+when_ :: (Monad m) => Bool -> m () -> m ()
+when_ True x = x
+when_ False _ = return ()
+
+-- vim: set ft=haskell :