initial codal support (#2935)
* Initial draft of codal support * bump pxt
This commit is contained in:
Родитель
00eb729501
Коммит
b29778ea60
30
README.md
30
README.md
|
@ -136,6 +136,36 @@ export PXT_NODOCKER=1
|
|||
|
||||
If you are also modifiying CODAL, consider running ``pxt clean`` to ensure the proper branch is picked up.
|
||||
|
||||
### Modifying DAL/CODAL locally
|
||||
|
||||
* follow instructions above until `pxt serve`
|
||||
* open editor on localhost and create a project
|
||||
* do `export PXT_FORCE_LOCAL=1 PXT_RUNTIME_DEV=1 PXT_ASMDEBUG=1`; you can add `PXT_NODOCKER=1`; `pxt help` has help on these
|
||||
* find project folder under `pxt-microbit/projects`, typically `pxt-microbit/projects/Untitled-42`
|
||||
* if you're going to modify `.cpp` files in PXT, replace `"core": "*"` in `pxt.json` with `"core": "file:../../libs/core"`;
|
||||
similarly `"radio": "file:../../libs/radio"`
|
||||
* you can edit `main.ts` to change the PXT side of the program; you can also edit it from the localhost editor;
|
||||
note that `Download` in the localhost editor will produce different binary than command line, as it builds in the cloud
|
||||
and uses tagged version of CODAL
|
||||
* in that folder run `pxt build` - this will clone codal somewhere under `built/` (depends on build engine and docker)
|
||||
* similarly, you can run `pxt deploy` (or just `pxt` which is the same) - it will build and copy to `MICROBIT` drive
|
||||
* assuming the build folder is under `built/codal`, go to `built/codal/libraries` and run `code *`
|
||||
* in git tab, checkout appropriate branches (they are all in detached head state to the way we tag releases)
|
||||
* modify files, run `pxt`, see effects
|
||||
* you can also run `pxt gdb` to debug; this requires `openocd`
|
||||
* other commands using `openocd` are `pxt dmesg` which dumps `DMESG(...)` buffer and `pxt heap` which can be used to visualize PXT heap
|
||||
(and CODAL's one to some extent)
|
||||
|
||||
### Updating dal.d.ts
|
||||
|
||||
```
|
||||
cd libs/blocksprj
|
||||
rm -rf built
|
||||
PXT_FORCE_LOCAL=1 PXT_COMPILE_SWITCHES=csv---mbcodal pxt build
|
||||
PXT_FORCE_LOCAL=1 PXT_COMPILE_SWITCHES=csv---mbcodal pxt builddaldts
|
||||
mv dal.d.ts ../core
|
||||
```
|
||||
|
||||
### Updates
|
||||
|
||||
Make sure to pull changes from all repos regularly. More instructions are at https://github.com/Microsoft/pxt#running-a-target-from-localhost
|
||||
|
|
|
@ -0,0 +1,121 @@
|
|||
/// <reference path="../node_modules/pxt-core/built/pxtcompiler.d.ts"/>
|
||||
|
||||
namespace ts.pxtc.extension {
|
||||
pxtc.compilerHooks.postBinary = (program: ts.Program, opts: CompileOptions, res: CompileResult) => {
|
||||
if (!opts.target.isNative)
|
||||
return
|
||||
const mbdal = res.outfiles["mbdal-binary.hex"]
|
||||
const mbcodal = res.outfiles["mbcodal-binary.hex"]
|
||||
if (!mbdal || !mbcodal)
|
||||
return
|
||||
|
||||
let outp = ""
|
||||
|
||||
wrapHex(mbdal, 0x00, [0x99, 0x01, 0xc0, 0xde])
|
||||
wrapHex(mbcodal, 0x0D, [0x99, 0x03, 0xc0, 0xde], true)
|
||||
|
||||
outp += ":00000001FF\n"
|
||||
|
||||
res.outfiles["binary.hex"] = outp
|
||||
|
||||
function hex2str(bytes: number[]) {
|
||||
return ts.pxtc.hexfile.hexBytes([bytes.length - 3].concat(bytes)) + "\n"
|
||||
}
|
||||
|
||||
function paddingString(len: number) {
|
||||
let r = ""
|
||||
const len0 = len
|
||||
while (len >= 44) {
|
||||
r += hex2str([0x00, 0x00, 0x0C,
|
||||
0x42, 0x42, 0x42, 0x42,
|
||||
0x42, 0x42, 0x42, 0x42,
|
||||
0x42, 0x42, 0x42, 0x42,
|
||||
0x42, 0x42, 0x42, 0x42])
|
||||
len -= 44
|
||||
}
|
||||
if (len >= 12) {
|
||||
const numBytes = (len - 11) >> 1
|
||||
const bytes = [0x00, 0x00, 0x0C]
|
||||
for (let i = 0; i < numBytes; ++i) bytes.push(0x42)
|
||||
const add = hex2str(bytes)
|
||||
r += add
|
||||
len -= add.length
|
||||
}
|
||||
while (len--)
|
||||
r += "\n"
|
||||
|
||||
U.assert(r.length == len0)
|
||||
|
||||
return r
|
||||
}
|
||||
|
||||
function addBlock(blk: string) {
|
||||
if (blk.length > 512) {
|
||||
console.log("TOO big!", blk)
|
||||
U.oops("block too big")
|
||||
}
|
||||
outp += blk + paddingString(512 - blk.length)
|
||||
}
|
||||
|
||||
function wrapHex(inpHex: string, dataType: number, deviceType: number[], keepSrc = false) {
|
||||
let blk = ""
|
||||
let upperAddr = 0
|
||||
let prevAddr = 0
|
||||
let currAddr = 0
|
||||
for (let line of inpHex.split(/\r?\n/)) {
|
||||
if (!line)
|
||||
continue
|
||||
const parsed = ts.pxtc.hexfile.parseHexRecord(line)
|
||||
switch (parsed.type) {
|
||||
case 0x00:
|
||||
currAddr = (upperAddr << 16) | parsed.addr
|
||||
if ((currAddr >> 10) != (prevAddr >> 10))
|
||||
flush()
|
||||
prevAddr = currAddr
|
||||
addData(hex2str(
|
||||
[parsed.addr >> 8, parsed.addr & 0xff, dataType]
|
||||
.concat(parsed.data)))
|
||||
break
|
||||
case 0x01:
|
||||
//addData(hex2str([0x00, 0x00, 0x01]))
|
||||
flush()
|
||||
if (keepSrc) break
|
||||
else return
|
||||
case 0x04:
|
||||
upperAddr = ((parsed.data[0] << 8) | parsed.data[1]) << 16
|
||||
break
|
||||
case 0x03:
|
||||
case 0x05:
|
||||
// ignore
|
||||
break
|
||||
case 0x0E:
|
||||
// src record
|
||||
addData(hex2str(
|
||||
[parsed.addr >> 8, parsed.addr & 0xff, 0x0E]
|
||||
.concat(parsed.data)))
|
||||
break
|
||||
default:
|
||||
U.oops(`unknown hex record type: ${line}`)
|
||||
break
|
||||
}
|
||||
}
|
||||
flush()
|
||||
|
||||
function addData(newData: string) {
|
||||
if (blk.length + newData.length > 512)
|
||||
flush()
|
||||
if (blk == "") {
|
||||
blk = hex2str([0x00, 0x00, 0x04, upperAddr >> 24, (upperAddr >> 16) & 0xff])
|
||||
+ hex2str([0x00, 0x00, 0x0A].concat(deviceType))
|
||||
}
|
||||
blk += newData
|
||||
}
|
||||
|
||||
function flush() {
|
||||
if (blk)
|
||||
addBlock(blk)
|
||||
blk = ""
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,12 @@
|
|||
{
|
||||
"compilerOptions": {
|
||||
"target": "es5",
|
||||
"noImplicitAny": true,
|
||||
"noImplicitReturns": true,
|
||||
"noImplicitThis": true,
|
||||
"declaration": true,
|
||||
"out": "../built/compiler.js",
|
||||
"newLine": "LF",
|
||||
"sourceMap": false
|
||||
}
|
||||
}
|
|
@ -1,4 +1,5 @@
|
|||
#!/bin/sh
|
||||
set -e
|
||||
yotta build
|
||||
arm-none-eabi-objdump -d `find -name main.c.o` > disasm
|
||||
node genapplet.js disasm Reset_Handler
|
||||
|
|
|
@ -4,6 +4,8 @@
|
|||
"keywords": [],
|
||||
"author": "",
|
||||
"license": "MIT",
|
||||
"dependencies": {},
|
||||
"dependencies": {
|
||||
"microbit-dal": "lancaster-university/microbit-dal#v2.1.1"
|
||||
},
|
||||
"bin": "./source"
|
||||
}
|
||||
|
|
|
@ -143,6 +143,7 @@ INLINE void murmur3_core_2(const uint8_t *data, uint32_t len, uint32_t *dst) {
|
|||
dst[1] = h1;
|
||||
}
|
||||
|
||||
#if 0
|
||||
int Reset_Handler(uint32_t *dst, uint8_t *ptr, uint32_t pageSize,
|
||||
uint32_t numPages) {
|
||||
uint32_t crcTable[256];
|
||||
|
@ -165,19 +166,23 @@ int Reset_Handler(uint32_t *dst, uint8_t *ptr, uint32_t pageSize,
|
|||
#endif
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if 1
|
||||
#include "nrf.h"
|
||||
|
||||
#if 0
|
||||
#define PAGE_SIZE 0x400
|
||||
#define SIZE_IN_WORDS (PAGE_SIZE / 4)
|
||||
|
||||
#define setConfig(v) \
|
||||
do { \
|
||||
NRF_NVMC->CONFIG = v; \
|
||||
__ISB(); __DSB(); \
|
||||
while (NRF_NVMC->READY == NVMC_READY_READY_Busy) \
|
||||
; \
|
||||
} while (0)
|
||||
|
||||
void overwriteFlashPage(uint32_t *to, uint32_t *from) {
|
||||
void Reset_Handler(uint32_t *to, uint32_t *from, uint32_t numWords) {
|
||||
#if 0
|
||||
int same = 1;
|
||||
for (int i = 0; i <= (SIZE_IN_WORDS - 1); i++) {
|
||||
if (to[i] != from[i]) {
|
||||
|
@ -187,6 +192,7 @@ void overwriteFlashPage(uint32_t *to, uint32_t *from) {
|
|||
}
|
||||
if (same)
|
||||
return;
|
||||
#endif
|
||||
|
||||
// Turn on flash erase enable and wait until the NVMC is ready:
|
||||
setConfig(NVMC_CONFIG_WEN_Een << NVMC_CONFIG_WEN_Pos);
|
||||
|
@ -202,7 +208,7 @@ void overwriteFlashPage(uint32_t *to, uint32_t *from) {
|
|||
// Turn on flash write enable and wait until the NVMC is ready:
|
||||
setConfig(NVMC_CONFIG_WEN_Wen << NVMC_CONFIG_WEN_Pos);
|
||||
|
||||
for (int i = 0; i <= (SIZE_IN_WORDS - 1); i++) {
|
||||
for (uint32_t i = 0; i < numWords; i++) {
|
||||
*(to + i) = *(from + i);
|
||||
while (NRF_NVMC->READY == NVMC_READY_READY_Busy)
|
||||
;
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
"dependencies": {
|
||||
"core": "file:../core"
|
||||
},
|
||||
"disablesVariants": ["mbcodal"],
|
||||
"yotta": {
|
||||
"config": {
|
||||
"microbit-dal": {
|
||||
|
|
|
@ -9,14 +9,18 @@ PXT_ABI(__aeabi_ddiv)
|
|||
PXT_ABI(__aeabi_dmul)
|
||||
|
||||
extern "C" void target_panic(int error_code) {
|
||||
#if !MICROBIT_CODAL
|
||||
// wait for serial to flush
|
||||
wait_us(300000);
|
||||
sleep_us(300000);
|
||||
#endif
|
||||
microbit_panic(error_code);
|
||||
}
|
||||
|
||||
#if !MICROBIT_CODAL
|
||||
extern "C" void target_reset() {
|
||||
microbit_reset();
|
||||
}
|
||||
#endif
|
||||
|
||||
uint32_t device_heap_size(uint8_t heap_index); // defined in microbit-dal
|
||||
|
||||
|
@ -27,7 +31,9 @@ MicroBitEvent lastEvent;
|
|||
|
||||
void platform_init() {
|
||||
microbit_seed_random();
|
||||
seedRandom(microbit_random(0x7fffffff));
|
||||
int seed = microbit_random(0x7fffffff);
|
||||
DMESG("random seed: %d", seed);
|
||||
seedRandom(seed);
|
||||
}
|
||||
|
||||
void initMicrobitGC() {
|
||||
|
@ -57,7 +63,10 @@ void deleteListener(MicroBitListener *l) {
|
|||
}
|
||||
|
||||
static void initCodal() {
|
||||
// TODO!!!
|
||||
#ifndef MICROBIT_CODAL
|
||||
uBit.messageBus.setListenerDeletionCallback(deleteListener);
|
||||
#endif
|
||||
|
||||
// repeat error 4 times and restart as needed
|
||||
microbit_panic_timeout(4);
|
||||
|
@ -91,7 +100,11 @@ void sleep_ms(unsigned ms) {
|
|||
}
|
||||
|
||||
void sleep_us(uint64_t us) {
|
||||
#if MICROBIT_CODAL
|
||||
target_wait_us(us);
|
||||
#else
|
||||
wait_us(us);
|
||||
#endif
|
||||
}
|
||||
|
||||
void forever_stub(void *a) {
|
||||
|
@ -231,10 +244,15 @@ void setThreadContext(ThreadContext *ctx) {
|
|||
currentFiber->user_data = ctx;
|
||||
}
|
||||
|
||||
#if !MICROBIT_CODAL
|
||||
#define tcb_get_stack_base(tcb) (tcb).stack_base
|
||||
#endif
|
||||
|
||||
static void *threadAddressFor(Fiber *fib, void *sp) {
|
||||
if (fib == currentFiber)
|
||||
return sp;
|
||||
return (uint8_t *)sp + ((uint8_t *)fib->stack_top - (uint8_t *)fib->tcb.stack_base);
|
||||
|
||||
return (uint8_t *)sp + ((uint8_t *)fib->stack_top - (uint8_t *)tcb_get_stack_base(fib->tcb));
|
||||
}
|
||||
|
||||
void gcProcessStacks(int flags) {
|
||||
|
@ -278,8 +296,10 @@ void gcProcessStacks(int flags) {
|
|||
for (auto seg = &ctx->stack; seg; seg = seg->next) {
|
||||
auto ptr = (TValue *)threadAddressFor(fib, seg->top);
|
||||
auto end = (TValue *)threadAddressFor(fib, seg->bottom);
|
||||
if (flags & 2)
|
||||
DMESG("RS%d:%p/%d", cnt++, ptr, end - ptr);
|
||||
if (flags & 2) {
|
||||
DMESG("RS%d:%p/%d", cnt, ptr, end - ptr);
|
||||
cnt++;
|
||||
}
|
||||
// VLOG("mark: %p - %p", ptr, end);
|
||||
while (ptr < end) {
|
||||
gcProcess(*ptr++);
|
||||
|
|
|
@ -274,7 +274,7 @@ namespace control {
|
|||
//% help=control/wait-micros weight=29
|
||||
//% blockId="control_wait_us" block="wait (µs)%micros"
|
||||
void waitMicros(int micros) {
|
||||
wait_us(micros);
|
||||
sleep_us(micros);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -297,7 +297,7 @@ namespace control {
|
|||
//% help=control/on-event
|
||||
//% blockExternalInputs=1
|
||||
void onEvent(int src, int value, Action handler, int flags = 0) {
|
||||
if (!flags) flags = EventFlags::QueueIfBusy;
|
||||
if (!flags) flags = ::EventFlags::QueueIfBusy;
|
||||
registerWithDal(src, value, handler, (int)flags);
|
||||
}
|
||||
|
||||
|
|
Разница между файлами не показана из-за своего большого размера
Загрузить разницу
|
@ -510,11 +510,11 @@ declare namespace led {
|
|||
|
||||
declare const enum PinEventType {
|
||||
//% block="edge"
|
||||
Edge = 1, // MICROBIT_PIN_EVENT_ON_EDGE
|
||||
Edge = 2, // MICROBIT_PIN_EVENT_ON_EDGE
|
||||
//% block="pulse"
|
||||
Pulse = 2, // MICROBIT_PIN_EVENT_ON_PULSE
|
||||
Pulse = 3, // MICROBIT_PIN_EVENT_ON_PULSE
|
||||
//% block="touch"
|
||||
Touch = 3, // MICROBIT_PIN_EVENT_ON_TOUCH
|
||||
Touch = 4, // MICROBIT_PIN_EVENT_ON_TOUCH
|
||||
//% block="none"
|
||||
None = 0, // MICROBIT_PIN_EVENT_NONE
|
||||
}
|
||||
|
|
|
@ -11,7 +11,7 @@ void RefMImage::destroy(RefMImage *t) {
|
|||
}
|
||||
|
||||
void RefMImage::print(RefMImage *t) {
|
||||
DMESG("RefMImage %p r=%d size=%d x %d", t, t->refcnt, img->width, img->height);
|
||||
DMESG("RefMImage %p size=%d x %d", t, t->img->width, t->img->height);
|
||||
}
|
||||
|
||||
void RefMImage::makeWritable() {
|
||||
|
|
|
@ -112,6 +112,10 @@ MicroBitPin *getPin(int id) {
|
|||
case MICROBIT_ID_IO_P16: return &uBit.io.P16;
|
||||
case MICROBIT_ID_IO_P19: return &uBit.io.P19;
|
||||
case MICROBIT_ID_IO_P20: return &uBit.io.P20;
|
||||
#if MICROBIT_CODAL
|
||||
case 1001: return &uBit.io.usbTx;
|
||||
case 1002: return &uBit.io.usbRx;
|
||||
#endif
|
||||
default: return NULL;
|
||||
}
|
||||
}
|
||||
|
@ -298,6 +302,7 @@ namespace pins {
|
|||
|
||||
|
||||
MicroBitPin* pitchPin = NULL;
|
||||
MicroBitPin* pitchPin2 = NULL;
|
||||
uint8_t pitchVolume = 64;
|
||||
|
||||
/**
|
||||
|
@ -310,6 +315,17 @@ namespace pins {
|
|||
//% name.fieldOptions.tooltips="false" name.fieldOptions.width="250"
|
||||
void analogSetPitchPin(AnalogPin name) {
|
||||
pitchPin = getPin((int)name);
|
||||
pitchPin2 = NULL;
|
||||
}
|
||||
|
||||
void pinAnalogSetPitch(MicroBitPin* pin, int frequency, int ms) {
|
||||
if (frequency <= 0 || pitchVolume == 0) {
|
||||
pin->setAnalogValue(0);
|
||||
} else {
|
||||
int v = 1 << (pitchVolume >> 5);
|
||||
pin->setAnalogValue(v);
|
||||
pin->setAnalogPeriodUs(1000000/frequency);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -340,22 +356,26 @@ namespace pins {
|
|||
//% blockId=device_analog_pitch block="analog pitch %frequency|for (ms) %ms"
|
||||
//% help=pins/analog-pitch weight=4 async advanced=true blockGap=8
|
||||
void analogPitch(int frequency, int ms) {
|
||||
if (pitchPin == NULL)
|
||||
analogSetPitchPin(AnalogPin::P0);
|
||||
if (frequency <= 0 || pitchVolume <= 0) {
|
||||
pitchPin->setAnalogValue(0);
|
||||
} else {
|
||||
// sound coming out of speaker is not linear, try best match
|
||||
int v = 1 << (pitchVolume >> 5);
|
||||
pitchPin->setAnalogValue(v);
|
||||
pitchPin->setAnalogPeriodUs(1000000/frequency);
|
||||
// init pins if needed
|
||||
if (NULL == pitchPin) {
|
||||
pitchPin = getPin((int)AnalogPin::P0);
|
||||
#ifdef SOUND_MIRROR_EXTENSION
|
||||
pitchPin2 = &SOUND_MIRROR_EXTENSION;
|
||||
#endif
|
||||
}
|
||||
|
||||
// set pitch
|
||||
if (NULL != pitchPin)
|
||||
pinAnalogSetPitch(pitchPin, frequency, ms);
|
||||
if (NULL != pitchPin2)
|
||||
pinAnalogSetPitch(pitchPin2, frequency, ms);
|
||||
// clear pitch
|
||||
if (ms > 0) {
|
||||
fiber_sleep(ms);
|
||||
if (NULL != pitchPin)
|
||||
pitchPin->setAnalogValue(0);
|
||||
// TODO why do we use wait_ms() here? it's a busy wait I think
|
||||
wait_ms(5);
|
||||
if (NULL != pitchPin2)
|
||||
pitchPin2->setAnalogValue(0);
|
||||
fiber_sleep(5);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -370,11 +390,19 @@ namespace pins {
|
|||
//% pin.fieldEditor="gridpicker" pin.fieldOptions.columns=4
|
||||
//% pin.fieldOptions.tooltips="false" pin.fieldOptions.width="250"
|
||||
void setPull(DigitalPin name, PinPullMode pull) {
|
||||
#if MICROBIT_CODAL
|
||||
codal::PullMode m = pull == PinPullMode::PullDown
|
||||
? codal::PullMode::Down
|
||||
: pull == PinPullMode::PullUp ? codal::PullMode::Up
|
||||
: codal::PullMode::None;
|
||||
PINOP(setPull(m));
|
||||
#else
|
||||
PinMode m = pull == PinPullMode::PullDown
|
||||
? PinMode::PullDown
|
||||
: pull == PinPullMode::PullUp ? PinMode::PullUp
|
||||
: PinMode::PullNone;
|
||||
PINOP(setPull(m));
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -401,6 +429,12 @@ namespace pins {
|
|||
return mkBuffer(NULL, size);
|
||||
}
|
||||
|
||||
#if MICROBIT_CODAL
|
||||
#define BUFFER_TYPE uint8_t*
|
||||
#else
|
||||
#define BUFFER_TYPE char*
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Read `size` bytes from a 7-bit I2C `address`.
|
||||
*/
|
||||
|
@ -408,7 +442,7 @@ namespace pins {
|
|||
Buffer i2cReadBuffer(int address, int size, bool repeat = false)
|
||||
{
|
||||
Buffer buf = createBuffer(size);
|
||||
uBit.i2c.read(address << 1, (char*)buf->data, size, repeat);
|
||||
uBit.i2c.read(address << 1, (BUFFER_TYPE)buf->data, size, repeat);
|
||||
return buf;
|
||||
}
|
||||
|
||||
|
@ -418,7 +452,7 @@ namespace pins {
|
|||
//%
|
||||
int i2cWriteBuffer(int address, Buffer buf, bool repeat = false)
|
||||
{
|
||||
return uBit.i2c.write(address << 1, (char*)buf->data, buf->length, repeat);
|
||||
return uBit.i2c.write(address << 1, (BUFFER_TYPE)buf->data, buf->length, repeat);
|
||||
}
|
||||
|
||||
SPI* spi = NULL;
|
||||
|
@ -462,6 +496,12 @@ namespace pins {
|
|||
p->format(bits, mode);
|
||||
}
|
||||
|
||||
#if MICROBIT_CODAL
|
||||
#define PIN_ARG(pin) *(getPin((int)(pin)))
|
||||
#else
|
||||
#define PIN_ARG(pin) (getPin((int)(pin)))->name
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Set the MOSI, MISO, SCK pins used by the SPI connection
|
||||
*
|
||||
|
@ -479,7 +519,6 @@ namespace pins {
|
|||
delete spi;
|
||||
spi = NULL;
|
||||
}
|
||||
|
||||
spi = new SPI(getPin((int)mosi)->name, getPin((int)miso)->name, getPin((int)sck)->name);
|
||||
spi = new SPI(PIN_ARG(mosi), PIN_ARG(miso), PIN_ARG(sck));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#include "nrf.h"
|
||||
|
||||
// helpful define to handle C++ differences in package
|
||||
#define PXT_MICROBIT_TAGGED_INT 1
|
||||
#define PXT_POWI 1
|
||||
|
|
|
@ -33,6 +33,12 @@ static inline ImageData *imageBytes(ImageLiteral_ lit) {
|
|||
return (ImageData *)lit;
|
||||
}
|
||||
|
||||
#if MICROBIT_CODAL
|
||||
// avoid clashes with codal-defined classes
|
||||
#define Image MImage
|
||||
#define Button MButton
|
||||
#endif
|
||||
|
||||
typedef RefMImage *Image;
|
||||
|
||||
extern MicroBit uBit;
|
||||
|
|
|
@ -53,6 +53,31 @@
|
|||
],
|
||||
"public": true,
|
||||
"dependencies": {},
|
||||
"dalDTS": {
|
||||
"compileServiceVariant": "mbcodal",
|
||||
"includeDirs": [
|
||||
"libraries/codal-core/inc",
|
||||
"libraries/codal-microbit/inc",
|
||||
"libraries/codal-microbit/model",
|
||||
"libraries/codal-microbit/inc/compat",
|
||||
"pxtapp"
|
||||
],
|
||||
"excludePrefix": [
|
||||
"USB_",
|
||||
"REQUEST_",
|
||||
"LIS3DH_",
|
||||
"FXOS8700_",
|
||||
"MMA8",
|
||||
"LSM303_",
|
||||
"MAG_",
|
||||
"MPU6050_",
|
||||
"REF_TAG_",
|
||||
"HF2_",
|
||||
"PXT_REF_TAG_",
|
||||
"MS_",
|
||||
"SCSI_"
|
||||
]
|
||||
},
|
||||
"yotta": {
|
||||
"config": {
|
||||
"microbit-dal": {
|
||||
|
|
|
@ -19,6 +19,18 @@ void debuglog(const char *format, ...);
|
|||
#define GC_BLOCK_SIZE 256
|
||||
#define NON_GC_HEAP_RESERVATION 1024
|
||||
|
||||
|
||||
#ifdef CODAL_CONFIG_H
|
||||
#define MICROBIT_CODAL 1
|
||||
#else
|
||||
#define MICROBIT_CODAL 0
|
||||
#endif
|
||||
|
||||
#if !MICROBIT_CODAL
|
||||
#undef DMESG
|
||||
#define DMESG NOLOG
|
||||
#endif
|
||||
|
||||
#undef BYTES_TO_WORDS
|
||||
|
||||
#endif
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
#define MICROBIT_SERIAL_READ_BUFFER_LENGTH 64
|
||||
|
||||
// make sure USB_TX and USB_RX don't overlap with other pin ids
|
||||
// also, 1001,1002 need to be kept in sync with getPin() function
|
||||
enum SerialPin {
|
||||
P0 = MICROBIT_ID_IO_P0,
|
||||
P1 = MICROBIT_ID_IO_P1,
|
||||
|
@ -145,12 +146,14 @@ namespace serial {
|
|||
|
||||
bool tryResolvePin(SerialPin p, PinName& name) {
|
||||
switch(p) {
|
||||
#if !MICROBIT_CODAL
|
||||
case SerialPin::USB_TX: name = USBTX; return true;
|
||||
case SerialPin::USB_RX: name = USBRX; return true;
|
||||
#endif
|
||||
default:
|
||||
auto pin = getPin(p);
|
||||
if (NULL != pin) {
|
||||
name = pin->name;
|
||||
name = (PinName)pin->name;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
@ -173,11 +176,17 @@ namespace serial {
|
|||
//% rx.fieldOptions.tooltips="false"
|
||||
//% blockGap=8
|
||||
void redirect(SerialPin tx, SerialPin rx, BaudRate rate) {
|
||||
#if MICROBIT_CODAL
|
||||
if (getPin(tx) && getPin(rx))
|
||||
uBit.serial.redirect(*getPin(tx), *getPin(rx));
|
||||
uBit.serial.setBaud(rate);
|
||||
#else
|
||||
PinName txn;
|
||||
PinName rxn;
|
||||
if (tryResolvePin(tx, txn) && tryResolvePin(rx, rxn))
|
||||
uBit.serial.redirect(txn, rxn);
|
||||
uBit.serial.baud((int)rate);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -186,8 +195,13 @@ namespace serial {
|
|||
//% weight=9 help=serial/redirect-to-usb
|
||||
//% blockId=serial_redirect_to_usb block="serial|redirect to USB"
|
||||
void redirectToUSB() {
|
||||
#if MICROBIT_CODAL
|
||||
uBit.serial.redirect(uBit.io.usbTx, uBit.io.usbRx);
|
||||
uBit.serial.setBaud(115200);
|
||||
#else
|
||||
uBit.serial.redirect(USBTX, USBRX);
|
||||
uBit.serial.baud(115200);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -0,0 +1,6 @@
|
|||
{
|
||||
"input": "Events and data from sensors",
|
||||
"input.onLoudSound": "Registers an event that runs when a loud sound is detected",
|
||||
"input.setLoudSoundThreshold": "Sets the minimum threshold for a loud sound",
|
||||
"input.soundLevel": "Reads the loudness through the microphone from 0 (silent) to 255 (loud)"
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"LoudnessCondition.Loud|block": "loud",
|
||||
"LoudnessCondition.Quiet|block": "quiet",
|
||||
"input.onLoudSound|block": "on loud sound",
|
||||
"input.setLoudSoundThreshold|block": "set loud sound threshold %value",
|
||||
"input.soundLevel|block": "sound level",
|
||||
"input|block": "input",
|
||||
"{id:category}Input": "Input",
|
||||
"{id:group}More": "More"
|
||||
}
|
|
@ -0,0 +1,13 @@
|
|||
{
|
||||
"additionalFilePath": "../../node_modules/pxt-common-packages/libs/microphone",
|
||||
"files": [
|
||||
"README.md",
|
||||
"microphone.cpp",
|
||||
"microphonehw.cpp",
|
||||
"enums.d.ts",
|
||||
"shims.d.ts"
|
||||
],
|
||||
"dependencies": {
|
||||
"core": "file:../core"
|
||||
}
|
||||
}
|
|
@ -0,0 +1,33 @@
|
|||
// Auto-generated. Do not edit.
|
||||
declare namespace input {
|
||||
|
||||
/**
|
||||
* Registers an event that runs when a loud sound is detected
|
||||
*/
|
||||
//% help=input/on-loud-sound
|
||||
//% blockId=input_on_loud_sound block="on loud sound"
|
||||
//% parts="microphone"
|
||||
//% weight=88 blockGap=12 shim=input::onLoudSound
|
||||
function onLoudSound(handler: () => void): void;
|
||||
|
||||
/**
|
||||
* Reads the loudness through the microphone from 0 (silent) to 255 (loud)
|
||||
*/
|
||||
//% help=input/sound-level
|
||||
//% blockId=device_get_sound_level block="sound level"
|
||||
//% parts="microphone"
|
||||
//% weight=34 blockGap=8 shim=input::soundLevel
|
||||
function soundLevel(): int32;
|
||||
|
||||
/**
|
||||
* Sets the minimum threshold for a loud sound
|
||||
*/
|
||||
//% help=input/set-loud-sound-threshold
|
||||
//% blockId=input_set_loud_sound_threshold block="set loud sound threshold %value"
|
||||
//% parts="microphone"
|
||||
//% value.min=1 value.max=255
|
||||
//% group="More" weight=14 blockGap=8 shim=input::setLoudSoundThreshold
|
||||
function setLoudSoundThreshold(value: int32): void;
|
||||
}
|
||||
|
||||
// Auto-generated. Do not edit. Really.
|
|
@ -11,7 +11,8 @@
|
|||
"libs/devices",
|
||||
"libs/bluetooth",
|
||||
"libs/servo",
|
||||
"libs/radio-broadcast"
|
||||
"libs/radio-broadcast",
|
||||
"libs/microphone"
|
||||
],
|
||||
"cloud": {
|
||||
"workspace": false,
|
||||
|
@ -112,6 +113,45 @@
|
|||
"webUSB": true,
|
||||
"useNewFunctions": true
|
||||
},
|
||||
"compileService": {
|
||||
"yottaTarget": "bbc-microbit-classic-gcc",
|
||||
"yottaCorePackage": "microbit",
|
||||
"githubCorePackage": "lancaster-university/microbit",
|
||||
"gittag": "v2.2.0-rc5",
|
||||
"serviceId": "microbit",
|
||||
"dockerImage": "pext/yotta:latest"
|
||||
},
|
||||
"multiVariants": [
|
||||
"mbdal",
|
||||
"mbcodal"
|
||||
],
|
||||
"variants": {
|
||||
"mbdal": {
|
||||
"compile": {},
|
||||
"compileService": {}
|
||||
},
|
||||
"mbcodal": {
|
||||
"compile": {
|
||||
"flashUsableEnd": null,
|
||||
"flashEnd": null
|
||||
},
|
||||
"compileService": {
|
||||
"buildEngine": "codal",
|
||||
"codalTarget": {
|
||||
"name": "codal-microbit",
|
||||
"url": "https://github.com/microbit-foundation/codal-microbit",
|
||||
"branch": "v0.1.0",
|
||||
"type": "git"
|
||||
},
|
||||
"codalBinary": "MICROBIT",
|
||||
"githubCorePackage": "microbit-foundation/codal",
|
||||
"gittag": "pxt-wip-build-v0.0.1",
|
||||
"serviceId": "mbcodal",
|
||||
"dockerImage": "pext/yotta:latest",
|
||||
"yottaConfigCompatibility": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"runtime": {
|
||||
"mathBlocks": true,
|
||||
"loopsBlocks": true,
|
||||
|
@ -243,14 +283,6 @@
|
|||
]
|
||||
}
|
||||
},
|
||||
"compileService": {
|
||||
"yottaTarget": "bbc-microbit-classic-gcc",
|
||||
"yottaCorePackage": "microbit",
|
||||
"githubCorePackage": "lancaster-university/microbit",
|
||||
"gittag": "v2.2.0-rc5",
|
||||
"serviceId": "microbit",
|
||||
"dockerImage": "pext/yotta:latest"
|
||||
},
|
||||
"serial": {
|
||||
"nameFilter": "^(mbed Serial Port|DAPLink CMSIS-DAP)",
|
||||
"log": true,
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
|
||||
namespace pxsim {
|
||||
export class DalBoard extends CoreBoard
|
||||
implements RadioBoard, LightBoard {
|
||||
implements RadioBoard, LightBoard, MicrophoneBoard {
|
||||
// state & update logic for component services
|
||||
ledMatrixState: LedMatrixState;
|
||||
edgeConnectorState: EdgeConnectorState;
|
||||
|
@ -15,6 +15,7 @@ namespace pxsim {
|
|||
lightSensorState: LightSensorState;
|
||||
buttonPairState: ButtonPairState;
|
||||
radioState: RadioState;
|
||||
microphoneState: AnalogSensorState;
|
||||
lightState: pxt.Map<CommonNeoPixelState>;
|
||||
fileSystem: FileSystemState;
|
||||
|
||||
|
@ -85,6 +86,7 @@ namespace pxsim {
|
|||
ID_RADIO: DAL.MICROBIT_ID_RADIO,
|
||||
RADIO_EVT_DATAGRAM: DAL.MICROBIT_RADIO_EVT_DATAGRAM
|
||||
});
|
||||
this.builtinParts["microphone"] = this.microphoneState = new AnalogSensorState(3001 /* DEVICE_ID_MICROPHONE */, 52, 120, 75, 96);
|
||||
this.builtinParts["accelerometer"] = this.accelerometerState = new AccelerometerState(runtime);
|
||||
this.builtinParts["serial"] = this.serialState = new SerialState();
|
||||
this.builtinParts["thermometer"] = this.thermometerState = new ThermometerState();
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
"*.ts",
|
||||
"state/*.ts",
|
||||
"visuals/*.ts",
|
||||
"../node_modules/pxt-common-packages/libs/core/sim/analogSensor.ts",
|
||||
"../node_modules/pxt-common-packages/libs/microphone/sim/*.ts",
|
||||
"../node_modules/pxt-common-packages/libs/core/sim/neopixel.ts",
|
||||
"../node_modules/pxt-common-packages/libs/radio/sim/*.ts"
|
||||
]
|
||||
|
|
Загрузка…
Ссылка в новой задаче