Merge remote-tracking branch 'origin/main' into supervisor-ticks

This commit is contained in:
Jeff Epler 2021-07-11 15:12:55 -05:00
commit 1600f11545
126 changed files with 1680 additions and 1356 deletions

View File

@ -1,54 +0,0 @@
---
name: Bug report
about: Create a report to help us improve
title: ''
labels: 'bug'
assignees: ''
---
<!-- Thanks! for testing out CircuitPython. Now that you have got a problem...
you can file a bug report for it. Feel free to modify the below format to better
suit your issue. :) -->
**Firmware**
<!-- Include the version of CircuitPython you're running. You can see it in the
`boot_out.txt` file, as well as in the REPL. -->
```python
Adafruit CircuitPython 6.2.0-beta.2 on 2021-03-01; Raspberry Pi Pico with rp2040
```
**Code/REPL**
<!-- Include your code that reproduces the bug here. Try to distill down to the
minimum possible to reproduce. -->
```python
import busio, bitbangio
i2c = bitbangio.I2C(board.GP1, board.GP0)
```
**Behavior**
<!-- What happens when you run the code above? Include any error messages. -->
```python
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TimeoutError: Clock stretch too long
```
**Description**
<!-- Optionally, describe the issue in more detail. Here are some examples: -->
- Error while using i2c...
- Only happens when...
- might be related to #4291...
**Additional Info**
<!-- Optionally, add any other information like hardware connection, scope output etc.
If you have already done some debugging, mention it here. -->

63
.github/ISSUE_TEMPLATE/bug_report.yml vendored Normal file
View File

@ -0,0 +1,63 @@
name: 🐞 Bug Report
description: Create a bug report to help us improve
labels:
- bug
body:
- type: markdown
attributes:
value: >-
Thanks! for testing out CircuitPython. Now that you have encountered a
bug... you can file a report for it.
- type: textarea
id: firmware
attributes:
label: CircuitPython version
description: >-
Include the version of CircuitPython you're running. You can see it in
the `boot_out.txt` file, as well as in the `REPL`.
placeholder: Adafruit CircuitPython 6.2.0 on 2021-03-01; Raspberry Pi Pico with rp2040
render: python
validations:
required: true
- type: textarea
id: code
attributes:
label: Code/REPL
description: This is automatically rendered as Python, so no need for backticks.
placeholder: |
import busio, bitbangio
i2c = bitbangio.I2C(board.GP1, board.GP0)
render: python
validations:
required: true
- type: textarea
id: behavior
attributes:
label: Behavior
description: What happens when you run the code above? Include error messages (if any).
placeholder: |
```python
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TimeoutError: Clock stretch too long
```
On-board led pulses red.
validations:
required: true
- type: textarea
id: description
attributes:
label: Description
description: Optionally, describe the bug in more detail.
placeholder: |
- Error while using i2c...
- Only happens when...
- might be related to #4291...
- type: textarea
id: more-info
attributes:
label: Additional information
description: >-
Optionally, add any other information like hardware connection, scope
output etc. If you have already done some debugging, mention it here.
placeholder: Removing [this](url) line resolves the issue.

View File

@ -1,7 +1,7 @@
contact_links:
- name: Adafruit Forum
- name: 🔗 Adafruit Forum
url: https://forums.adafruit.com/
about: Official Adafruit technical support forum. Good for getting help on getting a project working.
- name: Adafruit Discord
- name: 🔗 Adafruit Discord
url: https://adafru.it/discord
about: Unofficial chat with many helpful folks and normally prompt replies.

View File

@ -1,5 +1,5 @@
---
name: Feature request
name: 🚀 Feature Request
about: Suggest an idea for this project
title: ''
labels: 'enhancement'
@ -7,5 +7,5 @@ assignees: ''
---
<!-- We are always adding new features and enhancements to CircuitPython 🚀
<!-- We keep adding new features and enhancements to CircuitPython 🚀
and would love ❤ to see what new challenge you have got for us... 🙂 -->

View File

@ -414,7 +414,6 @@ texinfo_documents = [
# Example configuration for intersphinx: refer to the Python standard library.
intersphinx_mapping = {"cpython": ('https://docs.python.org/3/', None),
"bus_device": ('https://circuitpython.readthedocs.io/projects/busdevice/en/latest/', None),
"register": ('https://circuitpython.readthedocs.io/projects/register/en/latest/', None)}
# Adapted from sphinxcontrib-redirects

View File

@ -118,7 +118,8 @@ STATIC void add_generic_services(bleio_adapter_obj_t *adapter) {
SECURITY_MODE_NO_ACCESS,
248, // max length, from Bluetooth spec
false, // not fixed length
&generic_name_bufinfo
&generic_name_bufinfo,
NULL
);
uint16_t zero_16 = 0;
@ -140,7 +141,8 @@ STATIC void add_generic_services(bleio_adapter_obj_t *adapter) {
SECURITY_MODE_NO_ACCESS,
2, // max length, from Bluetooth spec
true, // fixed length
&zero_16_value
&zero_16_value,
NULL
);
// Generic Attribute Service setup.
@ -176,7 +178,8 @@ STATIC void add_generic_services(bleio_adapter_obj_t *adapter) {
SECURITY_MODE_NO_ACCESS,
4, // max length, from Bluetooth spec
true, // fixed length
&zero_32_value
&zero_32_value,
NULL
);
}

View File

@ -41,7 +41,7 @@
#define CCCD_INDICATE 0x2
void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self, bleio_service_obj_t *service, uint16_t handle, bleio_uuid_obj_t *uuid, bleio_characteristic_properties_t props, bleio_attribute_security_mode_t read_perm, bleio_attribute_security_mode_t write_perm, mp_int_t max_length, bool fixed_length, mp_buffer_info_t *initial_value_bufinfo) {
void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self, bleio_service_obj_t *service, uint16_t handle, bleio_uuid_obj_t *uuid, bleio_characteristic_properties_t props, bleio_attribute_security_mode_t read_perm, bleio_attribute_security_mode_t write_perm, mp_int_t max_length, bool fixed_length, mp_buffer_info_t *initial_value_bufinfo, const char *user_description) {
self->service = service;
self->uuid = uuid;
self->decl_handle = BLE_GATT_HANDLE_INVALID;
@ -66,7 +66,7 @@ void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self,
if (service->is_remote) {
self->handle = handle;
} else {
common_hal_bleio_service_add_characteristic(self->service, self, initial_value_bufinfo);
common_hal_bleio_service_add_characteristic(self->service, self, initial_value_bufinfo, user_description);
}
}

View File

@ -84,7 +84,8 @@ bool common_hal_bleio_service_get_is_secondary(bleio_service_obj_t *self) {
void common_hal_bleio_service_add_characteristic(bleio_service_obj_t *self,
bleio_characteristic_obj_t *characteristic,
mp_buffer_info_t *initial_value_bufinfo) {
mp_buffer_info_t *initial_value_bufinfo,
const char *user_description) {
if (self->handle != common_hal_bleio_adapter_obj.last_added_service_handle) {
mp_raise_bleio_BluetoothError(

View File

@ -36,7 +36,7 @@
#include "shared-bindings/_bleio/Descriptor.h"
#include "shared-bindings/_bleio/Service.h"
#include "shared-bindings/_bleio/UUID.h"
#include "supervisor/shared/bluetooth.h"
#include "supervisor/shared/bluetooth/bluetooth.h"
// UUID shared by all cccd's.
bleio_uuid_obj_t cccd_uuid;

@ -1 +1 @@
Subproject commit 40d8a03b4569d566faa62fcb0f798178118f2954
Subproject commit b014aa045d9014b86a4ae583f452c6b8282a61b9

View File

@ -54,6 +54,10 @@ msgstr " File \"%q\", baris %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr "output:\n"
@ -150,11 +154,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2064,6 +2063,10 @@ msgstr "Kesalahan Init SPI"
msgid "SPI Re-initialization error"
msgstr "Kesalahan Inisialisasi ulang SPI"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2549,7 +2552,7 @@ msgstr "Argumen argsort harus berupa ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "argumen memiliki tipe yang salah"

View File

@ -147,11 +147,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"

View File

@ -50,6 +50,10 @@ msgstr " Soubor \"%q\", řádek %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " výstup:\n"
@ -146,11 +150,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2033,6 +2032,10 @@ msgstr ""
msgid "SPI Re-initialization error"
msgstr ""
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2510,7 +2513,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr ""

View File

@ -53,6 +53,10 @@ msgstr " Datei \"%q\", Zeile %d"
msgid " is of type %q\n"
msgstr " ist vom Type %q\n"
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " Ausgabe:\n"
@ -151,11 +155,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2062,6 +2061,10 @@ msgstr "SPI-Init-Fehler"
msgid "SPI Re-initialization error"
msgstr "SPI-Neuinitialisierungsfehler"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2555,7 +2558,7 @@ msgstr "Das Argument argsort muss ein ndarray sein"
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "Argument hat falschen Typ"

View File

@ -47,6 +47,10 @@ msgstr ""
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr ""
@ -143,11 +147,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2030,6 +2029,10 @@ msgstr ""
msgid "SPI Re-initialization error"
msgstr ""
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2507,7 +2510,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr ""

View File

@ -55,6 +55,10 @@ msgstr " File \"%q\", line %d"
msgid " is of type %q\n"
msgstr " is of type %q\n"
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " output:\n"
@ -152,11 +156,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2058,6 +2057,10 @@ msgstr "SPI init error"
msgid "SPI Re-initialization error"
msgstr "SPI reinitialisation error"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr "SPI peripheral in use"
@ -2542,7 +2545,7 @@ msgstr "argsort argument must be an ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr "argsort is not implemented for flattened arrays"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "argument has wrong type"

View File

@ -8,7 +8,7 @@ msgstr ""
"Project-Id-Version: \n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-04 12:55-0600\n"
"PO-Revision-Date: 2021-06-24 23:11+0000\n"
"PO-Revision-Date: 2021-06-27 12:33+0000\n"
"Last-Translator: Alvaro Figueroa <alvaro@greencore.co.cr>\n"
"Language-Team: \n"
"Language: es\n"
@ -56,6 +56,10 @@ msgstr " Archivo \"%q\", línea %d"
msgid " is of type %q\n"
msgstr " es de tipo %q\n"
#: main.c
msgid " not found.\n"
msgstr " no encontrado.\n"
#: main.c
msgid " output:\n"
msgstr " salida:\n"
@ -154,11 +158,6 @@ msgstr "%q debe estar entre %d y %d"
msgid "%q must of type %q"
msgstr "%q debe ser de tipo %q"
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr "%q debe almacenar bytes"
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -893,7 +892,7 @@ msgstr "Trozo de datos debe seguir fmt chunk"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data not supported with directed advertising"
msgstr ""
msgstr "Datos sin capacidad de anuncio dirigido"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data too large for advertisement packet"
@ -1752,7 +1751,7 @@ msgstr ""
#: shared-bindings/_bleio/Adapter.c
msgid "Only connectable advertisements can be directed"
msgstr ""
msgstr "Solo se puede dirigir a los anuncios conectables"
#: ports/stm/common-hal/alarm/pin/PinAlarm.c
msgid "Only edge detection is available on this hardware"
@ -2086,6 +2085,10 @@ msgstr "Error de inicio de SPI"
msgid "SPI Re-initialization error"
msgstr "Error de reinicialización de SPI"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr "Configuración de SPI fallida"
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr "Periférico SPI en uso"
@ -2586,7 +2589,7 @@ msgstr "El argumento para argsort debe ser un ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr "El argot no está implementado para arrays aplanados"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "el argumento tiene un tipo erroneo"
@ -4508,6 +4511,9 @@ msgstr "zi debe ser de tipo flotante"
msgid "zi must be of shape (n_section, 2)"
msgstr "zi debe ser una forma (n_section,2)"
#~ msgid "%q must store bytes"
#~ msgstr "%q debe almacenar bytes"
#~ msgid "Buffer too large and unable to allocate"
#~ msgstr "Buffer demasiado grande e incapaz de asignar"

View File

@ -46,6 +46,10 @@ msgstr " File \"%q\", line %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " output:\n"
@ -143,11 +147,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2050,6 +2049,10 @@ msgstr ""
msgid "SPI Re-initialization error"
msgstr ""
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2535,7 +2538,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "may maling type ang argument"

View File

@ -56,6 +56,10 @@ msgstr " Fichier \"%q\", ligne %d"
msgid " is of type %q\n"
msgstr " est de type %q\n"
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " sortie :\n"
@ -154,11 +158,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2095,6 +2094,10 @@ msgstr "Erreur d'initialisation SPI"
msgid "SPI Re-initialization error"
msgstr "Erreur de réinitialisation SPI"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr "Périphérique SPI utilisé"
@ -2588,7 +2591,7 @@ msgstr "Le paramêtre argsort doit être un ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr "argsort n'est pas mis en œuvre pour les matrices aplatis"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "l'argument est d'un mauvais type"

View File

@ -47,6 +47,10 @@ msgstr ""
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr ""
@ -143,11 +147,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2030,6 +2029,10 @@ msgstr ""
msgid "SPI Re-initialization error"
msgstr ""
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2507,7 +2510,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr ""

View File

@ -55,6 +55,10 @@ msgstr " File \"%q\", riga %d"
msgid " is of type %q\n"
msgstr " è di tipo %q\n"
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " output:\n"
@ -153,11 +157,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2069,6 +2068,10 @@ msgstr ""
msgid "SPI Re-initialization error"
msgstr ""
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2550,7 +2553,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "il tipo dell'argomento è errato"

View File

@ -52,6 +52,10 @@ msgstr " ファイル \"%q\", 行 %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " 出力:\n"
@ -148,11 +152,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2044,6 +2043,10 @@ msgstr "SPI初期化エラー"
msgid "SPI Re-initialization error"
msgstr "SPI再初期化エラー"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2522,7 +2525,7 @@ msgstr "argsortの引数はndarrayでなければなりません"
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr ""

View File

@ -48,6 +48,10 @@ msgstr " 파일 \"%q\", 라인 %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " 산출:\n"
@ -144,11 +148,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2033,6 +2032,10 @@ msgstr ""
msgid "SPI Re-initialization error"
msgstr ""
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2511,7 +2514,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr ""

View File

@ -50,6 +50,10 @@ msgstr " Bestand \"%q\", regel %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " uitvoer:\n"
@ -146,11 +150,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2060,6 +2059,10 @@ msgstr "SPI Init Fout"
msgid "SPI Re-initialization error"
msgstr "SPI Herinitialisatie Fout"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2548,7 +2551,7 @@ msgstr "argsort argument moet een ndarray zijn"
msgid "argsort is not implemented for flattened arrays"
msgstr "argsort wordt niet geïmplementeerd voor vlakke arrays"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "argument heeft onjuist type"

View File

@ -52,6 +52,10 @@ msgstr " Plik \"%q\", linia %d"
msgid " is of type %q\n"
msgstr ""
#: main.c
msgid " not found.\n"
msgstr ""
#: main.c
msgid " output:\n"
msgstr " wyjście:\n"
@ -148,11 +152,6 @@ msgstr ""
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -2041,6 +2040,10 @@ msgstr "Błąd inicjowania SPI"
msgid "SPI Re-initialization error"
msgstr "Błąd ponownej inicjalizacji SPI"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr ""
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr ""
@ -2524,7 +2527,7 @@ msgstr ""
msgid "argsort is not implemented for flattened arrays"
msgstr ""
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "argument ma zły typ"

View File

@ -6,7 +6,7 @@ msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-04 12:55-0600\n"
"PO-Revision-Date: 2021-06-24 23:11+0000\n"
"PO-Revision-Date: 2021-06-30 17:19+0000\n"
"Last-Translator: Wellington Terumi Uemura <wellingtonuemura@gmail.com>\n"
"Language-Team: \n"
"Language: pt_BR\n"
@ -54,6 +54,10 @@ msgstr " Arquivo \"%q\", linha %d"
msgid " is of type %q\n"
msgstr " é do tipo %q\n"
#: main.c
msgid " not found.\n"
msgstr " não encontrado.\n"
#: main.c
msgid " output:\n"
msgstr " saída:\n"
@ -152,11 +156,6 @@ msgstr "%q deve estar entre %d e %d"
msgid "%q must of type %q"
msgstr "o %q deve ser do tipo %q"
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr "o %q deve armazenar bytes"
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
msgid "%q out of range"
@ -896,7 +895,7 @@ msgstr "Pedaço de dados deve seguir o pedaço de cortes"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data not supported with directed advertising"
msgstr ""
msgstr "Os dados não são compatíveis com publicidade direcionada"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data too large for advertisement packet"
@ -1750,7 +1749,7 @@ msgstr ""
#: shared-bindings/_bleio/Adapter.c
msgid "Only connectable advertisements can be directed"
msgstr ""
msgstr "Somente anúncios conectáveis podem ser direcionados"
#: ports/stm/common-hal/alarm/pin/PinAlarm.c
msgid "Only edge detection is available on this hardware"
@ -2087,6 +2086,10 @@ msgstr "Houve um erro na inicialização SPI"
msgid "SPI Re-initialization error"
msgstr "Houve um erro na reinicialização SPI"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr "A configuração SPI falhou"
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr "O periférico SPI está em uso"
@ -2591,7 +2594,7 @@ msgstr "O argumento argsort deve ser um ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr "argsort não é implementado para matrizes achatadas"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "argumento tem tipo errado"
@ -4518,6 +4521,9 @@ msgstr "zi deve ser de um tipo float"
msgid "zi must be of shape (n_section, 2)"
msgstr "zi deve estar na forma (n_section, 2)"
#~ msgid "%q must store bytes"
#~ msgstr "o %q deve armazenar bytes"
#~ msgid "Buffer too large and unable to allocate"
#~ msgstr "O buffer é muito grande e incapaz de alocar"

View File

@ -6,7 +6,7 @@ msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-04 12:55-0600\n"
"PO-Revision-Date: 2021-06-24 12:16+0000\n"
"PO-Revision-Date: 2021-06-27 12:33+0000\n"
"Last-Translator: Jonny Bergdahl <jonny@bergdahl.it>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"Language: sv\n"
@ -54,6 +54,10 @@ msgstr " Fil \"%q\", rad %d"
msgid " is of type %q\n"
msgstr " är av typen %q\n"
#: main.c
msgid " not found.\n"
msgstr " hittades inte.\n"
#: main.c
msgid " output:\n"
msgstr " utdata:\n"
@ -93,7 +97,7 @@ msgstr "Indexet %q måste vara ett heltal, inte %s"
#: py/argcheck.c
msgid "%q length must be %q"
msgstr ""
msgstr "längden på %q måste vara %q"
#: shared-bindings/vectorio/Polygon.c
msgid "%q list must be a list"
@ -101,11 +105,11 @@ msgstr "%q-listan måste vara en lista"
#: py/argcheck.c
msgid "%q must <= %d"
msgstr ""
msgstr "%q måste vara <=%d"
#: py/argcheck.c
msgid "%q must be %d-%d"
msgstr ""
msgstr "%q måste vara %d-%d"
#: shared-bindings/usb_hid/Device.c
msgid "%q must be 0-255"
@ -117,7 +121,7 @@ msgstr "%q måste vara 1-255"
#: py/argcheck.c
msgid "%q must be >= %d"
msgstr ""
msgstr "%q måste vara >= %d"
#: py/argcheck.c shared-bindings/memorymonitor/AllocationAlarm.c
msgid "%q must be >= 0"
@ -137,7 +141,7 @@ msgstr "%q måste vara None eller mellan 1 och len(report_descriptor)-1"
#: py/argcheck.c
msgid "%q must be a string"
msgstr ""
msgstr "%q måste vara en sträng"
#: shared-module/vectorio/Polygon.c
msgid "%q must be a tuple of length 2"
@ -149,12 +153,7 @@ msgstr "%q måste vara mellan %d och %d"
#: py/argcheck.c
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
msgstr "%q måste av typen %q"
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
@ -886,7 +885,7 @@ msgstr "Datasegmentet måste följa fmt-segmentet"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data not supported with directed advertising"
msgstr ""
msgstr "Data stöds inte med riktad annonsering"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data too large for advertisement packet"
@ -1734,7 +1733,7 @@ msgstr ""
#: shared-bindings/_bleio/Adapter.c
msgid "Only connectable advertisements can be directed"
msgstr ""
msgstr "Endast anslutningsbara annonseringar kan dirigeras"
#: ports/stm/common-hal/alarm/pin/PinAlarm.c
msgid "Only edge detection is available on this hardware"
@ -2066,6 +2065,10 @@ msgstr "SPI Init-fel"
msgid "SPI Re-initialization error"
msgstr "SPI reinitialiseringsfel"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr "SPI-konfigurationen misslyckades"
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr "SPI-enhet används redan"
@ -2561,7 +2564,7 @@ msgstr "argumentet argsort måste vara en ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr "argsort är inte implementerad för tillplattade matriser"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "argumentet har fel typ"
@ -4477,6 +4480,9 @@ msgstr "zi måste vara av typ float"
msgid "zi must be of shape (n_section, 2)"
msgstr "zi måste vara i formen (n_section, 2)"
#~ msgid "%q must store bytes"
#~ msgstr "%q måste lagra bytes"
#~ msgid "Buffer too large and unable to allocate"
#~ msgstr "Bufferten är för stor och kan inte allokeras"

View File

@ -7,7 +7,7 @@ msgstr ""
"Project-Id-Version: circuitpython-cn\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-04 12:55-0600\n"
"PO-Revision-Date: 2021-06-23 17:15+0000\n"
"PO-Revision-Date: 2021-07-06 16:32+0000\n"
"Last-Translator: hexthat <hexthat@gmail.com>\n"
"Language-Team: Chinese Hanyu Pinyin\n"
"Language: zh_Latn_pinyin\n"
@ -15,7 +15,7 @@ msgstr ""
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=1; plural=0;\n"
"X-Generator: Weblate 4.7.1-dev\n"
"X-Generator: Weblate 4.8-dev\n"
#: main.c
msgid ""
@ -55,6 +55,10 @@ msgstr " Wénjiàn \"%q\", dì %d xíng"
msgid " is of type %q\n"
msgstr " shì %q lèi xíng\n"
#: main.c
msgid " not found.\n"
msgstr " wèi zhǎo dào.\n"
#: main.c
msgid " output:\n"
msgstr " shūchū:\n"
@ -95,7 +99,7 @@ msgstr "%q suǒyǐn bìxū shì zhěngshù, ér bùshì %s"
#: py/argcheck.c
msgid "%q length must be %q"
msgstr ""
msgstr "%q cháng dù bì xū wéi %q"
#: shared-bindings/vectorio/Polygon.c
msgid "%q list must be a list"
@ -103,11 +107,11 @@ msgstr "%q lièbiǎo bìxū shì lièbiǎo"
#: py/argcheck.c
msgid "%q must <= %d"
msgstr ""
msgstr "%q bì xū <= %d"
#: py/argcheck.c
msgid "%q must be %d-%d"
msgstr ""
msgstr "%q bì xū wéi %d-%d"
#: shared-bindings/usb_hid/Device.c
msgid "%q must be 0-255"
@ -119,7 +123,7 @@ msgstr "%q bì xū wéi 1-255"
#: py/argcheck.c
msgid "%q must be >= %d"
msgstr ""
msgstr "%q bì xū >= %d"
#: py/argcheck.c shared-bindings/memorymonitor/AllocationAlarm.c
msgid "%q must be >= 0"
@ -139,7 +143,7 @@ msgstr "%q bì xū wéi wú huò zài 1 hé len(report_descriptor)-1 zhī jiān"
#: py/argcheck.c
msgid "%q must be a string"
msgstr ""
msgstr "%q bì xū shì yí gè zì fú chuàn"
#: shared-module/vectorio/Polygon.c
msgid "%q must be a tuple of length 2"
@ -151,12 +155,7 @@ msgstr "%q bì xū zài %d hé %d zhī jiān"
#: py/argcheck.c
msgid "%q must of type %q"
msgstr ""
#: shared-bindings/keypad/KeyMatrix.c shared-bindings/keypad/Keys.c
#: shared-bindings/keypad/ShiftRegisterKeys.c
msgid "%q must store bytes"
msgstr ""
msgstr "%q bì xū lèi xíng %q"
#: ports/raspberrypi/common-hal/rp2pio/StateMachine.c
#: shared-bindings/canio/Match.c
@ -535,7 +534,7 @@ msgstr "Bǐtè shízhōng hé dānzì xuǎnzé bìxū gòngxiǎng shízhōng dā
#: shared-bindings/rgbmatrix/RGBMatrix.c
#, c-format
msgid "Bit depth must be from 1 to 6 inclusive, not %d"
msgstr "wèi shēn dù bì xū bāo hán 1 dào 6 ér bù shì %d"
msgstr "wèi shēn dù bì xū bāo hán 1 dào 6, ér bù shì %d"
#: shared-bindings/audiobusio/PDMIn.c
msgid "Bit depth must be multiple of 8."
@ -610,7 +609,7 @@ msgstr "Huǎnchōng qū bìxū zhìshǎo chángdù 1"
#: shared-bindings/_bleio/PacketBuffer.c
#, c-format
msgid "Buffer too short by %d bytes"
msgstr "Huǎn chōng qū tài duǎn àn %d zì jié"
msgstr "Huǎn chōng qū tài duǎn , àn %d zì jié"
#: ports/atmel-samd/common-hal/displayio/ParallelBus.c
#: ports/esp32s2/common-hal/displayio/ParallelBus.c
@ -885,7 +884,7 @@ msgstr "Shùjù kuài bìxū zūnxún fmt qū kuài"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data not supported with directed advertising"
msgstr ""
msgstr "bù zhī chí dìng xiàng guǎng gào de shù jù"
#: ports/nrf/common-hal/_bleio/Adapter.c
msgid "Data too large for advertisement packet"
@ -1737,7 +1736,7 @@ msgstr ""
#: shared-bindings/_bleio/Adapter.c
msgid "Only connectable advertisements can be directed"
msgstr ""
msgstr "zhǐ yǒu kě lián jiē de guǎng gào cái néng bèi yǐn dǎo"
#: ports/stm/common-hal/alarm/pin/PinAlarm.c
msgid "Only edge detection is available on this hardware"
@ -2065,6 +2064,10 @@ msgstr "SPI chūshǐhuà cuòwù"
msgid "SPI Re-initialization error"
msgstr "SPI chóngxīn chūshǐhuà cuòwù"
#: ports/esp32s2/common-hal/busio/SPI.c
msgid "SPI configuration failed"
msgstr "SPI pèi zhì shī bài"
#: ports/raspberrypi/common-hal/busio/SPI.c
msgid "SPI peripheral in use"
msgstr "SPI wài shè zhèng zài shǐ yòng zhōng"
@ -2169,7 +2172,7 @@ msgid ""
"Increase the stack size if you know how. If not:"
msgstr ""
"diàn lù dàn duī bèi sǔn huài, yīn wéi duī zhàn tài xiǎo.\n"
"rú guǒ nín zhī dào rú hé zēng jiā duī zhàn dà xiǎo. rú guǒ méi yǒu"
"rú guǒ nín zhī dào rú hé zēng jiā duī zhàn dà xiǎo. rú guǒ méi yǒu:"
#: supervisor/shared/safe_mode.c
msgid ""
@ -2351,7 +2354,7 @@ msgstr "Wúfǎ xiě rù nvm."
#: shared-bindings/alarm/SleepMemory.c
msgid "Unable to write to sleep_memory."
msgstr "wú fǎ xiě rù sleep_memory"
msgstr "wú fǎ xiě rù sleep_memory."
#: ports/nrf/common-hal/_bleio/UUID.c
msgid "Unexpected nrfx uuid type"
@ -2560,7 +2563,7 @@ msgstr "argsort cānshù bìxū shì ndarray"
msgid "argsort is not implemented for flattened arrays"
msgstr "wèi wéi pīn hé shù zǔ shí xiàn argsort"
#: py/runtime.c
#: py/runtime.c shared-bindings/supervisor/__init__.c
msgid "argument has wrong type"
msgstr "cānshù lèixíng cuòwù"
@ -2637,7 +2640,7 @@ msgstr "èrjìnzhì bǎn qián bǎn %q wèi zhíxíng"
#: extmod/modurandom.c
msgid "bits must be 32 or less"
msgstr ""
msgstr "wèi bì xū shì 32 huò gèng shǎo"
#: shared-bindings/busio/UART.c
msgid "bits must be in range 5 to 9"
@ -3258,7 +3261,7 @@ msgstr "túxíng bìxū wèi 2048 zì jié"
#: extmod/moduhashlib.c
msgid "hash is final"
msgstr ""
msgstr "hā xī shì zuì zhōng de"
#: extmod/moduheapq.c
msgid "heap must be a list"
@ -3411,7 +3414,7 @@ msgstr "wúxiào de cānshù"
#: shared-bindings/bitmaptools/__init__.c
#, c-format
msgid "invalid bits_per_pixel %d, must be, 1, 4, 8, 16, 24, or 32"
msgstr "wú xiào bits_per_pixel %d bì xū shì, 1, 4, 8, 16, 24, huò 32"
msgstr "wú xiào bits_per_pixel %d, bì xū shì, 1, 4, 8, 16, 24, huò 32"
#: shared-bindings/bitmaptools/__init__.c
#, c-format
@ -3870,7 +3873,7 @@ msgstr "chāo gāo zhuǎnhuàn zhǎng zhěng shùzì shí"
#: py/modstruct.c
#, c-format
msgid "pack expected %d items for packing (got %d)"
msgstr "bāo zhuāng yù qī de %d bāo zhuāng xiàng mù dé dào %d)"
msgstr "bāo zhuāng yù qī de %d bāo zhuāng xiàng mù (dé dào %d)"
#: shared-bindings/_stage/Layer.c shared-bindings/_stage/Text.c
msgid "palette must be 32 bytes long"
@ -4474,8 +4477,11 @@ msgstr "zi bìxū wèi fú diǎn xíng"
msgid "zi must be of shape (n_section, 2)"
msgstr "zi bìxū jùyǒu xíngzhuàng (n_section,2)"
#~ msgid "%q must store bytes"
#~ msgstr "%q bì xū cún chǔ zì jié"
#~ msgid "Buffer too large and unable to allocate"
#~ msgstr "Huǎn chōng qū tài dà wú fǎ fēn pèi"
#~ msgstr "Huǎn chōng qū tài dà , wú fǎ fēn pèi"
#~ msgid "interp is defined for 1D arrays of equal length"
#~ msgstr "interp shì wèi děng zhǎng de 1D shùzǔ dìngyì de"

2
main.c
View File

@ -71,7 +71,7 @@
#if CIRCUITPY_BLEIO
#include "shared-bindings/_bleio/__init__.h"
#include "supervisor/shared/bluetooth.h"
#include "supervisor/shared/bluetooth/bluetooth.h"
#endif
#if CIRCUITPY_BOARD

View File

@ -131,7 +131,7 @@ void audio_dma_load_next_block(audio_dma_t *dma) {
uint8_t *buffer;
uint32_t buffer_length;
audioio_get_buffer_result_t get_buffer_result =
audiosample_get_buffer(dma->sample, dma->single_channel, dma->audio_channel,
audiosample_get_buffer(dma->sample, dma->single_channel_output, dma->audio_channel,
&buffer, &buffer_length);
DmacDescriptor *descriptor = dma->second_descriptor;
@ -155,7 +155,7 @@ void audio_dma_load_next_block(audio_dma_t *dma) {
descriptor->SRCADDR.reg = ((uint32_t)output_buffer) + output_buffer_length;
if (get_buffer_result == GET_BUFFER_DONE) {
if (dma->loop) {
audiosample_reset_buffer(dma->sample, dma->single_channel, dma->audio_channel);
audiosample_reset_buffer(dma->sample, dma->single_channel_output, dma->audio_channel);
} else {
descriptor->DESCADDR.reg = 0;
}
@ -183,7 +183,7 @@ static void setup_audio_descriptor(DmacDescriptor *descriptor, uint8_t beat_size
audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
mp_obj_t sample,
bool loop,
bool single_channel,
bool single_channel_output,
uint8_t audio_channel,
bool output_signed,
uint32_t output_register_address,
@ -195,7 +195,7 @@ audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
dma->sample = sample;
dma->loop = loop;
dma->single_channel = single_channel;
dma->single_channel_output = single_channel_output;
dma->audio_channel = audio_channel;
dma->dma_channel = dma_channel;
dma->signed_to_unsigned = false;
@ -203,12 +203,12 @@ audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
dma->second_descriptor = NULL;
dma->spacing = 1;
dma->first_descriptor_free = true;
audiosample_reset_buffer(sample, single_channel, audio_channel);
audiosample_reset_buffer(sample, single_channel_output, audio_channel);
bool single_buffer;
bool samples_signed;
uint32_t max_buffer_length;
audiosample_get_buffer_structure(sample, single_channel, &single_buffer, &samples_signed,
audiosample_get_buffer_structure(sample, single_channel_output, &single_buffer, &samples_signed,
&max_buffer_length, &dma->spacing);
uint8_t output_spacing = dma->spacing;
if (output_signed != samples_signed) {
@ -254,12 +254,12 @@ audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
} else {
dma->beat_size = 1;
dma->bytes_per_sample = 1;
if (single_channel) {
if (single_channel_output) {
output_register_address += 1;
}
}
// Transfer both channels at once.
if (!single_channel && audiosample_channel_count(sample) == 2) {
if (!single_channel_output && audiosample_channel_count(sample) == 2) {
dma->beat_size *= 2;
}

View File

@ -42,7 +42,7 @@ typedef struct {
uint8_t beat_size;
uint8_t spacing;
bool loop;
bool single_channel;
bool single_channel_output;
bool signed_to_unsigned;
bool unsigned_to_signed;
bool first_buffer_free;
@ -72,16 +72,16 @@ void dma_free_channel(uint8_t channel);
// This sets everything up but doesn't start the timer.
// Sample is the python object for the sample to play.
// loop is true if we should loop the sample.
// single_channel is true if we only output a single channel. When false, all channels will be
// single_channel_output is true if we only output a single channel. When false, all channels will be
// output.
// audio_channel is the index of the channel to dma. single_channel must be false in this case.
// audio_channel is the index of the channel to dma. single_channel_output must be false in this case.
// output_signed is true if the dma'd data should be signed. False and it will be unsigned.
// output_register_address is the address to copy data to.
// dma_trigger_source is the DMA trigger source which cause another copy
audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
mp_obj_t sample,
bool loop,
bool single_channel,
bool single_channel_output,
uint8_t audio_channel,
bool output_signed,
uint32_t output_register_address,

View File

@ -9,3 +9,5 @@ CHIP_FAMILY = samd21
INTERNAL_FLASH_FILESYSTEM = 1
LONGINT_IMPL = NONE
CIRCUITPY_FULL_BUILD = 0
CIRCUITPY_USB_MIDI = 0

View File

@ -6,6 +6,8 @@ USB_MANUFACTURER = "Electronic Cats"
CHIP_VARIANT = SAMD21G18A
CHIP_FAMILY = samd21
CIRCUITPY_PWMIO = 0
INTERNAL_FLASH_FILESYSTEM = 1
LONGINT_IMPL = NONE
CIRCUITPY_FULL_BUILD = 0

View File

@ -30,14 +30,17 @@ CIRCUIPTY_USB_CDC = 0
CIRCUITPY_USB_HID = 0
CIRCUITPY_USB_MIDI = 0
CIRCUITPY_VECTORIO = 0
CIRCUITPY_GAMEPAD = 0
CIRCUITPY_PWMIO = 0
CIRCUITPY_ANALOGIO = 1
CIRCUITPY_AUDIOMIXER = 1
CIRCUITPY_AUDIOIO = 1
CIRCUITPY_SYNTHIO = 1
CIRCUITPY_DISPLAYIO = 1
CIRCUITPY_GAMEPAD = 1
CIRCUITPY_MATH = 1
CIRCUITPY_STAGE = 1
CIRCUITPY_KEYPAD = 1
FROZEN_MPY_DIRS += $(TOP)/frozen/circuitpython-stage/pewpew_m4
CIRCUITPY_DISPLAY_FONT = $(TOP)/ports/atmel-samd/boards/ugame10/brutalist-6.bdf

View File

@ -92,11 +92,13 @@
#ifdef SAMD21
#ifndef CIRCUITPY_INTERNAL_FLASH_FILESYSTEM_SIZE
#if INTERNAL_FLASH_FILESYSTEM
#define CIRCUITPY_INTERNAL_FLASH_FILESYSTEM_SIZE (64 * 1024)
#else
#define CIRCUITPY_INTERNAL_FLASH_FILESYSTEM_SIZE (0)
#endif
#endif
#ifndef CIRCUITPY_INTERNAL_NVM_SIZE
#define CIRCUITPY_INTERNAL_NVM_SIZE (256)

View File

@ -118,8 +118,12 @@ void common_hal_busio_spi_construct(busio_spi_obj_t *self,
void common_hal_busio_spi_never_reset(busio_spi_obj_t *self) {
spi_never_reset[self->host_id] = true;
common_hal_never_reset_pin(self->clock);
common_hal_never_reset_pin(self->MOSI);
common_hal_never_reset_pin(self->MISO);
if (self->MOSI != NULL) {
common_hal_never_reset_pin(self->MOSI);
}
if (self->MISO != NULL) {
common_hal_never_reset_pin(self->MISO);
}
}
bool common_hal_busio_spi_deinited(busio_spi_obj_t *self) {

View File

@ -18,6 +18,7 @@ CIRCUITPY_AUDIOBUSIO = 1
CIRCUITPY_AUDIOBUSIO_PDMIN = 0
CIRCUITPY_AUDIOBUSIO_I2SOUT = 1
CIRCUITPY_AUDIOIO = 0
CIRCUITPY_AUDIOMIXER = 1
CIRCUITPY_CANIO = 1
CIRCUITPY_COUNTIO = 1
CIRCUITPY_DUALBANK = 1

View File

@ -41,11 +41,6 @@
#include "common-hal/audiopwmio/PWMAudioOut.h"
#endif
#if CIRCUITPY_BLEIO
#include "supervisor/shared/bluetooth.h"
#include "common-hal/_bleio/bonding.h"
#endif
void port_start_background_task(void) {
}
void port_finish_background_task(void) {

View File

@ -38,8 +38,6 @@
#include "py/misc.h"
#include "py/mpstate.h"
#include "supervisor/shared/bluetooth.h"
nrf_nvic_state_t nrf_nvic_state = { 0 };
// Flag indicating progress of internal flash operation.

View File

@ -1,191 +0,0 @@
/*
* This file is part of the MicroPython project, http://micropython.org/
*
* The MIT License (MIT)
*
* Copyright (c) 2019 Dan Halbert for Adafruit Industries
* Copyright (c) 2018 Artur Pacholec
* Copyright (c) 2017 Glenn Ruben Bakke
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#include <string.h>
#include "ble.h"
#include "ble_uart.h"
#include "ringbuffer.h"
#include "py/mphal.h"
#include "py/runtime.h"
#include "lib/utils/interrupt_char.h"
#include "shared-bindings/_bleio/Adapter.h"
#include "shared-bindings/_bleio/Characteristic.h"
#include "shared-bindings/_bleio/Device.h"
#include "shared-bindings/_bleio/Service.h"
#include "shared-bindings/_bleio/UUID.h"
#if CIRCUITPY_CONSOLE_BLE
static const char default_name[] = "CP-REPL"; // max 8 chars or uuid won't fit in adv data
static const char NUS_UUID[] = "6e400001-b5a3-f393-e0a9-e50e24dcca9e";
#define NUS_RX_UUID 0x0002
#define NUS_TX_UUID 0x0003
#define BUFFER_SIZE 128
ringBuffer_typedef(uint8_t, ringbuffer_t);
static bleio_device_obj_t m_device;
static bleio_service_obj_t *m_nus;
static bleio_characteristic_obj_t *m_tx_chara;
static bleio_characteristic_obj_t *m_rx_chara;
static volatile bool m_cccd_enabled;
static uint8_t m_rx_ring_buffer_data[BUFFER_SIZE];
static ringbuffer_t m_rx_ring_buffer = {
.size = sizeof(m_rx_ring_buffer_data) + 1,
.elems = m_rx_ring_buffer_data,
};
STATIC void on_ble_evt(ble_evt_t *ble_evt, void *param) {
switch (ble_evt->header.evt_id) {
case BLE_GAP_EVT_DISCONNECTED: {
mp_obj_t device_obj = MP_OBJ_FROM_PTR(&m_device);
mp_call_function_0(mp_load_attr(device_obj, qstr_from_str("start_advertising")));
break;
}
case BLE_GATTS_EVT_WRITE: {
ble_gatts_evt_write_t *write = &ble_evt->evt.gatts_evt.params.write;
if (write->handle == m_tx_chara->cccd_handle) {
m_cccd_enabled = true;
} else if (write->handle == m_rx_chara->handle) {
for (size_t i = 0; i < write->len; ++i) {
#if MICROPY_KBD_EXCEPTION
if (write->data[i] == mp_interrupt_char) {
mp_sched_keyboard_interrupt();
} else
#endif
{
bufferWrite(&m_rx_ring_buffer, write->data[i]);
}
}
}
}
}
}
void ble_uart_init(void) {
mp_obj_t device_obj = MP_OBJ_FROM_PTR(&m_device);
m_device.base.type = &bleio_device_type;
m_device.service_list = mp_obj_new_list(0, NULL);
m_device.notif_handler = mp_const_none;
m_device.conn_handler = mp_const_none;
m_device.conn_handle = 0xFFFF;
m_device.is_peripheral = true;
m_device.name = mp_obj_new_str(default_name, strlen(default_name), false);
common_hal_bleio_adapter_get_address(&m_device.address);
mp_obj_t nus_uuid_str = mp_obj_new_str(NUS_UUID, strlen(NUS_UUID), false);
mp_obj_t nus_uuid_obj = bleio_uuid_type.make_new(&bleio_uuid_type, 1, 0, &nus_uuid_str);
mp_obj_t nus_obj = bleio_service_type.make_new(&bleio_service_type, 1, 0, &nus_uuid_obj);
m_nus = MP_OBJ_TO_PTR(nus_obj);
mp_call_function_1(mp_load_attr(device_obj, qstr_from_str("add_service")), nus_obj);
mp_obj_t tx_uuid_int = mp_obj_new_int(NUS_TX_UUID);
mp_obj_t tx_uuid_obj = bleio_uuid_type.make_new(&bleio_uuid_type, 1, 0, &tx_uuid_int);
mp_obj_t tx_obj = bleio_characteristic_type.make_new(&bleio_characteristic_type, 1, 0, &tx_uuid_obj);
m_tx_chara = MP_OBJ_TO_PTR(tx_obj);
m_tx_chara->uuid->type = UUID_TYPE_128BIT;
m_tx_chara->uuid->uuid_vs_idx = m_nus->uuid->uuid_vs_idx;
m_tx_chara->props.notify = true;
mp_call_function_1(mp_load_attr(nus_obj, qstr_from_str("add_characteristic")), tx_obj);
mp_obj_t rx_uuid_int = mp_obj_new_int(NUS_RX_UUID);
mp_obj_t rx_uuid_obj = bleio_uuid_type.make_new(&bleio_uuid_type, 1, 0, &rx_uuid_int);
mp_obj_t rx_obj = bleio_characteristic_type.make_new(&bleio_characteristic_type, 1, 0, &rx_uuid_obj);
m_rx_chara = MP_OBJ_TO_PTR(rx_obj);
m_rx_chara->uuid->type = UUID_TYPE_128BIT;
m_rx_chara->uuid->uuid_vs_idx = m_nus->uuid->uuid_vs_idx;
m_rx_chara->props.write = true;
m_rx_chara->props.write_wo_resp = true;
mp_call_function_1(mp_load_attr(nus_obj, qstr_from_str("add_characteristic")), rx_obj);
mp_call_function_0(mp_load_attr(device_obj, qstr_from_str("start_advertising")));
ble_drv_add_event_handler(on_ble_evt, &m_device);
m_cccd_enabled = false;
while (!m_cccd_enabled) {
RUN_BACKGROUND_TASKS;
}
}
bool ble_uart_connected(void) {
return m_device.conn_handle != BLE_CONN_HANDLE_INVALID;
}
char ble_uart_rx_chr(void) {
while (isBufferEmpty(&m_rx_ring_buffer)) {
RUN_BACKGROUND_TASKS;
}
uint8_t byte;
bufferRead(&m_rx_ring_buffer, byte);
return (int)byte;
}
bool ble_uart_stdin_any(void) {
return !isBufferEmpty(&m_rx_ring_buffer);
}
void ble_uart_stdout_tx_str(const char *text) {
mp_hal_stdout_tx_strn(text, strlen(text));
}
int mp_hal_stdin_rx_chr(void) {
return ble_uart_rx_chr();
}
void mp_hal_stdout_tx_strn(const char *str, size_t len) {
size_t send_len;
while (len > 0) {
if (len >= BLE_GATT_ATT_MTU_DEFAULT - 3) {
send_len = (BLE_GATT_ATT_MTU_DEFAULT - 3);
} else {
send_len = len;
}
mp_buffer_info_t bufinfo = {
.buf = (uint8_t *)str,
.len = send_len,
};
common_hal_bleio_characteristic_write_value(m_tx_chara, &bufinfo);
len -= send_len;
str += send_len;
}
}
#endif // CIRCUITPY_CONSOLE_BLE

View File

@ -1,99 +0,0 @@
/* The MIT License (MIT)
*
* Copyright (c) 2013 Philip Thrasher
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the "Software"), to deal in
* the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
* the Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
* COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
* Philip Thrasher's Crazy Awesome Ring Buffer Macros!
*
* Below you will find some naughty macros for easy owning and manipulating
* generic ring buffers. Yes, they are slightly evil in readability, but they
* are really fast, and they work great.
*
* Example usage:
*
* #include <stdio.h>
*
* // So we can use this in any method, this gives us a typedef
* // named 'intBuffer'.
* ringBuffer_typedef(int, intBuffer);
*
* int main() {
* // Declare vars.
* intBuffer myBuffer;
*
* bufferInit(myBuffer,1024,int);
*
* // We must have the pointer. All of the macros deal with the pointer.
* // (except for init.)
* intBuffer* myBuffer_ptr;
* myBuffer_ptr = &myBuffer;
*
* // Write two values.
* bufferWrite(myBuffer_ptr,37);
* bufferWrite(myBuffer_ptr,72);
*
* // Read a value into a local variable.
* int first;
* bufferRead(myBuffer_ptr,first);
* assert(first == 37); // true
*
* int second;
* bufferRead(myBuffer_ptr,second);
* assert(second == 72); // true
*
* return 0;
* }
*
*/
#ifndef _ringbuffer_h
#define _ringbuffer_h
#define ringBuffer_typedef(T, NAME) \
typedef struct { \
int size; \
volatile int start; \
volatile int end; \
T *elems; \
} NAME
#define bufferInit(BUF, S, T) \
BUF.size = S + 1; \
BUF.start = 0; \
BUF.end = 0; \
BUF.elems = (T *)calloc(BUF.size, sizeof(T))
#define bufferDestroy(BUF) free((BUF)->elems)
#define nextStartIndex(BUF) (((BUF)->start + 1) % (BUF)->size)
#define nextEndIndex(BUF) (((BUF)->end + 1) % (BUF)->size)
#define isBufferEmpty(BUF) ((BUF)->end == (BUF)->start)
#define isBufferFull(BUF) (nextEndIndex(BUF) == (BUF)->start)
#define bufferWrite(BUF, ELEM) \
(BUF)->elems[(BUF)->end] = ELEM; \
(BUF)->end = ((BUF)->end + 1) % (BUF)->size; \
if (isBufferEmpty(BUF)) { \
(BUF)->start = nextStartIndex(BUF); \
}
#define bufferRead(BUF, ELEM) \
ELEM = (BUF)->elems[(BUF)->start]; \
(BUF)->start = nextStartIndex(BUF);
#endif

View File

@ -27,6 +27,7 @@ CIRCUITPY_RE = 0
CIRCUITPY_RGBMATRIX = 0
CIRCUITPY_SDCARDIO = 0
CIRCUITPY_ULAB = 0
CIRCUITPY_USB_MIDI = 0
MICROPY_PY_ASYNC_AWAIT = 0

View File

@ -43,3 +43,5 @@ CIRCUITPY_WATCHDOG = 1
# Override optimization to keep binary small
OPTIMIZATION_FLAGS = -Os
SUPEROPT_VM = 0
SUPEROPT_GC = 0

View File

@ -40,7 +40,7 @@
#include "py/gc.h"
#include "py/objstr.h"
#include "py/runtime.h"
#include "supervisor/shared/bluetooth.h"
#include "supervisor/shared/bluetooth/bluetooth.h"
#include "supervisor/shared/safe_mode.h"
#include "supervisor/shared/tick.h"
#include "supervisor/usb.h"

View File

@ -86,7 +86,8 @@ STATIC void characteristic_gatts_notify_indicate(uint16_t handle, uint16_t conn_
void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self, bleio_service_obj_t *service,
uint16_t handle, bleio_uuid_obj_t *uuid, bleio_characteristic_properties_t props,
bleio_attribute_security_mode_t read_perm, bleio_attribute_security_mode_t write_perm,
mp_int_t max_length, bool fixed_length, mp_buffer_info_t *initial_value_bufinfo) {
mp_int_t max_length, bool fixed_length, mp_buffer_info_t *initial_value_bufinfo,
const char *user_description) {
self->service = service;
self->uuid = uuid;
self->handle = BLE_GATT_HANDLE_INVALID;
@ -125,7 +126,7 @@ void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self,
if (service->is_remote) {
self->handle = handle;
} else {
common_hal_bleio_service_add_characteristic(self->service, self, initial_value_bufinfo);
common_hal_bleio_service_add_characteristic(self->service, self, initial_value_bufinfo, user_description);
}
}

View File

@ -80,20 +80,34 @@ STATIC bool characteristic_buffer_on_ble_evt(ble_evt_t *ble_evt, void *param) {
return true;
}
void _common_hal_bleio_characteristic_buffer_construct(bleio_characteristic_buffer_obj_t *self,
bleio_characteristic_obj_t *characteristic,
mp_float_t timeout,
uint8_t *buffer, size_t buffer_size,
void *static_handler_entry) {
self->characteristic = characteristic;
self->timeout_ms = timeout * 1000;
self->ringbuf.buf = (uint8_t *)buffer;
self->ringbuf.size = buffer_size;
self->ringbuf.iget = 0;
self->ringbuf.iput = 0;
if (static_handler_entry != NULL) {
ble_drv_add_event_handler_entry((ble_drv_evt_handler_entry_t *)static_handler_entry, characteristic_buffer_on_ble_evt, self);
} else {
ble_drv_add_event_handler(characteristic_buffer_on_ble_evt, self);
}
}
// Assumes that timeout and buffer_size have been validated before call.
void common_hal_bleio_characteristic_buffer_construct(bleio_characteristic_buffer_obj_t *self,
bleio_characteristic_obj_t *characteristic,
mp_float_t timeout,
size_t buffer_size) {
self->characteristic = characteristic;
self->timeout_ms = timeout * 1000;
// This is a macro.
// true means long-lived, so it won't be moved.
ringbuf_alloc(&self->ringbuf, buffer_size, true);
ble_drv_add_event_handler(characteristic_buffer_on_ble_evt, self);
uint8_t *buffer = m_malloc(buffer_size, true);
_common_hal_bleio_characteristic_buffer_construct(self, characteristic, timeout, buffer, buffer_size, NULL);
}
uint32_t common_hal_bleio_characteristic_buffer_read(bleio_characteristic_buffer_obj_t *self, uint8_t *data, size_t len, int *errcode) {

View File

@ -533,7 +533,8 @@ STATIC void on_char_discovery_rsp(ble_gattc_evt_char_disc_rsp_t *response, bleio
characteristic, m_char_discovery_service, gattc_char->handle_value, uuid,
props, SECURITY_MODE_OPEN, SECURITY_MODE_OPEN,
GATT_MAX_DATA_LENGTH, false, // max_length, fixed_length: values don't matter for gattc
mp_const_empty_bytes);
mp_const_empty_bytes,
NULL);
mp_obj_list_append(MP_OBJ_FROM_PTR(m_char_discovery_service->characteristic_list),
MP_OBJ_FROM_PTR(characteristic));

View File

@ -173,6 +173,23 @@ STATIC bool packet_buffer_on_ble_server_evt(ble_evt_t *ble_evt, void *param) {
}
break;
}
case BLE_GAP_EVT_CONN_SEC_UPDATE: { // 0x1a
if (self->conn_handle != BLE_CONN_HANDLE_INVALID) {
break;
}
uint16_t conn_handle = ble_evt->evt.gatts_evt.conn_handle;
// Check to see if the bond restored the HVX state.
uint16_t cccd;
ble_gatts_value_t value;
value.len = sizeof(uint16_t);
value.offset = 0;
value.p_value = (uint8_t *)&cccd;
sd_ble_gatts_value_get(conn_handle, self->characteristic->cccd_handle, &value);
if (cccd & BLE_GATT_HVX_NOTIFICATION) {
self->conn_handle = conn_handle;
}
break;
}
case BLE_GAP_EVT_CONNECTED:
break;
case BLE_GAP_EVT_DISCONNECTED:

View File

@ -112,7 +112,8 @@ STATIC void _expand_range(uint16_t new_value, uint16_t *start, uint16_t *end) {
void common_hal_bleio_service_add_characteristic(bleio_service_obj_t *self,
bleio_characteristic_obj_t *characteristic,
mp_buffer_info_t *initial_value_bufinfo) {
mp_buffer_info_t *initial_value_bufinfo,
const char *user_description) {
ble_gatts_char_md_t char_md = {
.char_props.broadcast = (characteristic->props & CHAR_PROP_BROADCAST) ? 1 : 0,
.char_props.read = (characteristic->props & CHAR_PROP_READ) ? 1 : 0,
@ -142,6 +143,18 @@ void common_hal_bleio_service_add_characteristic(bleio_service_obj_t *self,
char_md.p_cccd_md = &cccd_md;
}
ble_gatts_attr_md_t user_desc_md;
if (user_description != NULL && strlen(user_description) > 0) {
BLE_GAP_CONN_SEC_MODE_SET_OPEN(&user_desc_md.read_perm);
// If the description is on the Python heap, then have the SD copy it. If not, assume it's
// static and will live for longer than the SD.
user_desc_md.vloc = gc_nbytes(user_description) > 0 ? BLE_GATTS_VLOC_STACK : BLE_GATTS_VLOC_USER;
char_md.p_user_desc_md = &user_desc_md;
char_md.p_char_user_desc = (const uint8_t *)user_description;
char_md.char_user_desc_max_size = strlen(user_description);
char_md.char_user_desc_size = strlen(user_description);
}
bleio_attribute_gatts_set_security_mode(&char_attr_md.read_perm, characteristic->read_perm);
bleio_attribute_gatts_set_security_mode(&char_attr_md.write_perm, characteristic->write_perm);
#if CIRCUITPY_VERBOSE_BLE

View File

@ -36,7 +36,7 @@
#include "shared-bindings/_bleio/Descriptor.h"
#include "shared-bindings/_bleio/Service.h"
#include "shared-bindings/_bleio/UUID.h"
#include "supervisor/shared/bluetooth.h"
#include "supervisor/shared/bluetooth/bluetooth.h"
#include "common-hal/_bleio/__init__.h"
#include "common-hal/_bleio/bonding.h"
@ -96,6 +96,8 @@ void check_sec_status(uint8_t sec_status) {
// Turn off BLE on a reset or reload.
void bleio_reset() {
// Set this explicitly to save data.
common_hal_bleio_adapter_obj.base.type = &bleio_adapter_type;
if (!common_hal_bleio_adapter_get_enabled(&common_hal_bleio_adapter_obj)) {
return;
}
@ -107,12 +109,8 @@ void bleio_reset() {
}
// The singleton _bleio.Adapter object, bound to _bleio.adapter
// It currently only has properties and no state
bleio_adapter_obj_t common_hal_bleio_adapter_obj = {
.base = {
.type = &bleio_adapter_type,
},
};
// It currently only has properties and no state. Inited by bleio_reset
bleio_adapter_obj_t common_hal_bleio_adapter_obj;
void common_hal_bleio_check_connected(uint16_t conn_handle) {
if (conn_handle == BLE_CONN_HANDLE_INVALID) {

View File

@ -51,7 +51,7 @@
#endif
// These are in order from highest available frequency to lowest (32MHz first, then 8MHz).
STATIC spim_peripheral_t spim_peripherals[] = {
STATIC const spim_peripheral_t spim_peripherals[] = {
#if NRFX_CHECK(NRFX_SPIM3_ENABLED)
// SPIM3 exists only on nRF52840 and supports 32MHz max. All other SPIM's are only 8MHz max.
// Allocate SPIM3 first.

View File

@ -38,7 +38,7 @@ typedef struct {
typedef struct {
mp_obj_base_t base;
spim_peripheral_t *spim_peripheral;
const spim_peripheral_t *spim_peripheral;
bool has_lock;
uint8_t clock_pin_number;
uint8_t MOSI_pin_number;

View File

@ -1,68 +0,0 @@
from ubluepy import Peripheral, constants
BLE_GAP_ADV_FLAG_LE_GENERAL_DISC_MODE = const(0x02)
BLE_GAP_ADV_FLAG_BR_EDR_NOT_SUPPORTED = const(0x04)
BLE_GAP_ADV_FLAGS_LE_ONLY_GENERAL_DISC_MODE = const(
BLE_GAP_ADV_FLAG_LE_GENERAL_DISC_MODE | BLE_GAP_ADV_FLAG_BR_EDR_NOT_SUPPORTED
)
EDDYSTONE_FRAME_TYPE_URL = const(0x10)
EDDYSTONE_URL_PREFIX_HTTP_WWW = const(0x00) # "http://www".
EDDYSTONE_URL_SUFFIX_DOT_COM = const(0x01) # ".com"
def string_to_binarray(text):
b = bytearray([])
for c in text:
b.append(ord(c))
return b
def gen_ad_type_content(ad_type, data):
b = bytearray(1)
b.append(ad_type)
b.extend(data)
b[0] = len(b) - 1
return b
def generate_eddystone_adv_packet(url):
# flags
disc_mode = bytearray([BLE_GAP_ADV_FLAGS_LE_ONLY_GENERAL_DISC_MODE])
packet_flags = gen_ad_type_content(constants.ad_types.AD_TYPE_FLAGS, disc_mode)
# 16-bit uuid
uuid = bytearray([0xAA, 0xFE])
packet_uuid16 = gen_ad_type_content(
constants.ad_types.AD_TYPE_16BIT_SERVICE_UUID_COMPLETE, uuid
)
# eddystone data
rssi = 0xEE # -18 dB, approx signal strength at 0m.
eddystone_data = bytearray([])
eddystone_data.append(EDDYSTONE_FRAME_TYPE_URL)
eddystone_data.append(rssi)
eddystone_data.append(EDDYSTONE_URL_PREFIX_HTTP_WWW)
eddystone_data.extend(string_to_binarray(url))
eddystone_data.append(EDDYSTONE_URL_SUFFIX_DOT_COM)
# service data
service_data = uuid + eddystone_data
packet_service_data = gen_ad_type_content(
constants.ad_types.AD_TYPE_SERVICE_DATA, service_data
)
# generate advertisement packet
packet = bytearray([])
packet.extend(packet_flags)
packet.extend(packet_uuid16)
packet.extend(packet_service_data)
return packet
def start():
adv_packet = generate_eddystone_adv_packet("micropython")
p = Peripheral()
p.advertise(data=adv_packet, connectable=False)

View File

@ -1,42 +0,0 @@
from ubluepy import Scanner, constants
def bytes_to_str(bytes):
string = ""
for b in bytes:
string += chr(b)
return string
def get_device_names(scan_entries):
dev_names = []
for e in scan_entries:
scan = e.getScanData()
if scan:
for s in scan:
if s[0] == constants.ad_types.AD_TYPE_COMPLETE_LOCAL_NAME:
dev_names.append((e, bytes_to_str(s[2])))
return dev_names
def find_device_by_name(name):
s = Scanner()
scan_res = s.scan(100)
device_names = get_device_names(scan_res)
for dev in device_names:
if name == dev[1]:
return dev[0]
# >>> res = find_device_by_name("micr")
# >>> if res:
# ... print("address:", res.addr())
# ... print("address type:", res.addr_type())
# ... print("rssi:", res.rssi())
# ...
# ...
# ...
# address: c2:73:61:89:24:45
# address type: 1
# rssi: -26

View File

@ -1,94 +0,0 @@
# This file is part of the MicroPython project, http://micropython.org/
#
# The MIT License (MIT)
#
# SPDX-FileCopyrightText: Copyright (c) 2017 Glenn Ruben Bakke
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
# THE SOFTWARE
from pyb import LED
from machine import RTC, Temp
from ubluepy import Service, Characteristic, UUID, Peripheral, constants
def event_handler(id, handle, data):
global rtc
global periph
global serv_env_sense
global notif_enabled
if id == constants.EVT_GAP_CONNECTED:
# indicated 'connected'
LED(1).on()
elif id == constants.EVT_GAP_DISCONNECTED:
# stop low power timer
rtc.stop()
# indicate 'disconnected'
LED(1).off()
# restart advertisement
periph.advertise(device_name="micr_temp", services=[serv_env_sense])
elif id == constants.EVT_GATTS_WRITE:
# write to this Characteristic is to CCCD
if int(data[0]) == 1:
notif_enabled = True
# start low power timer
rtc.start()
else:
notif_enabled = False
# stop low power timer
rtc.stop()
def send_temp(timer_id):
global notif_enabled
global char_temp
if notif_enabled:
# measure chip temperature
temp = Temp.read()
temp = temp * 100
char_temp.write(bytearray([temp & 0xFF, temp >> 8]))
# start off with LED(1) off
LED(1).off()
# use RTC1 as RTC0 is used by bluetooth stack
# set up RTC callback every 5 second
rtc = RTC(1, period=5, mode=RTC.PERIODIC, callback=send_temp)
notif_enabled = False
uuid_env_sense = UUID("0x181A") # Environmental Sensing service
uuid_temp = UUID("0x2A6E") # Temperature characteristic
serv_env_sense = Service(uuid_env_sense)
temp_props = Characteristic.PROP_NOTIFY | Characteristic.PROP_READ
temp_attrs = Characteristic.ATTR_CCCD
char_temp = Characteristic(uuid_temp, props=temp_props, attrs=temp_attrs)
serv_env_sense.addCharacteristic(char_temp)
periph = Peripheral()
periph.addService(serv_env_sense)
periph.setConnectionHandler(event_handler)
periph.advertise(device_name="micr_temp", services=[serv_env_sense])

View File

@ -50,6 +50,9 @@ CIRCUITPY_ALARM ?= 1
# Turn on the BLE file service
CIRCUITPY_BLE_FILE_SERVICE ?= 1
# Turn on the BLE serial service
CIRCUITPY_SERIAL_BLE ?= 1
CIRCUITPY_COMPUTED_GOTO_SAVE_SPACE ?= 1
# nRF52840-specific

View File

@ -129,7 +129,7 @@ void audio_dma_load_next_block(audio_dma_t *dma) {
uint8_t *buffer;
uint32_t buffer_length;
get_buffer_result = audiosample_get_buffer(dma->sample,
dma->single_channel, dma->audio_channel, &buffer, &buffer_length);
dma->single_channel_output, dma->audio_channel, &buffer, &buffer_length);
if (get_buffer_result == GET_BUFFER_ERROR) {
audio_dma_stop(dma);
@ -148,7 +148,7 @@ void audio_dma_load_next_block(audio_dma_t *dma) {
dma_channel_set_read_addr(dma_channel, output_buffer, false /* trigger */);
if (get_buffer_result == GET_BUFFER_DONE) {
if (dma->loop) {
audiosample_reset_buffer(dma->sample, dma->single_channel, dma->audio_channel);
audiosample_reset_buffer(dma->sample, dma->single_channel_output, dma->audio_channel);
} else {
// Set channel trigger to ourselves so we don't keep going.
dma_channel_hw_t *c = &dma_hw->ch[dma_channel];
@ -161,26 +161,31 @@ void audio_dma_load_next_block(audio_dma_t *dma) {
audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
mp_obj_t sample,
bool loop,
bool single_channel,
bool single_channel_output,
uint8_t audio_channel,
bool output_signed,
uint8_t output_resolution,
uint32_t output_register_address,
uint8_t dma_trigger_source) {
// Use two DMA channels to because the DMA can't wrap to itself without the
// Use two DMA channels to play because the DMA can't wrap to itself without the
// buffer being power of two aligned.
dma->channel[0] = dma_claim_unused_channel(false);
dma->channel[1] = dma_claim_unused_channel(false);
if (dma->channel[0] == NUM_DMA_CHANNELS || dma->channel[1] == NUM_DMA_CHANNELS) {
if (dma->channel[0] < NUM_DMA_CHANNELS) {
dma_channel_unclaim(dma->channel[0]);
}
int dma_channel_0_maybe = dma_claim_unused_channel(false);
if (dma_channel_0_maybe < 0) {
return AUDIO_DMA_DMA_BUSY;
}
int dma_channel_1_maybe = dma_claim_unused_channel(false);
if (dma_channel_1_maybe < 0) {
dma_channel_unclaim((uint)dma_channel_0_maybe);
return AUDIO_DMA_DMA_BUSY;
}
dma->channel[0] = (uint8_t)dma_channel_0_maybe;
dma->channel[1] = (uint8_t)dma_channel_1_maybe;
dma->sample = sample;
dma->loop = loop;
dma->single_channel = single_channel;
dma->single_channel_output = single_channel_output;
dma->audio_channel = audio_channel;
dma->signed_to_unsigned = false;
dma->unsigned_to_signed = false;
@ -189,12 +194,12 @@ audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
dma->first_channel_free = true;
dma->output_resolution = output_resolution;
dma->sample_resolution = audiosample_bits_per_sample(sample);
audiosample_reset_buffer(sample, single_channel, audio_channel);
audiosample_reset_buffer(sample, single_channel_output, audio_channel);
bool single_buffer;
bool samples_signed;
uint32_t max_buffer_length;
audiosample_get_buffer_structure(sample, single_channel, &single_buffer, &samples_signed,
audiosample_get_buffer_structure(sample, single_channel_output, &single_buffer, &samples_signed,
&max_buffer_length, &dma->sample_spacing);
// Check to see if we have to scale the resolution up.
@ -227,10 +232,9 @@ audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
dma->output_size = 1;
}
// Transfer both channels at once.
if (!single_channel && audiosample_channel_count(sample) == 2) {
if (!single_channel_output && audiosample_channel_count(sample) == 2) {
dma->output_size *= 2;
}
enum dma_channel_transfer_size dma_size = DMA_SIZE_8;
if (dma->output_size == 2) {
dma_size = DMA_SIZE_16;
@ -324,20 +328,19 @@ void audio_dma_stop(audio_dma_t *dma) {
// to hold the previous value.
void audio_dma_pause(audio_dma_t *dma) {
dma_hw->ch[dma->channel[0]].al1_ctrl &= ~DMA_CH0_CTRL_TRIG_EN_BITS;
dma_hw->ch[dma->channel[1]].al1_ctrl &= ~DMA_CH0_CTRL_TRIG_EN_BITS;
dma_hw->ch[dma->channel[1]].al1_ctrl &= ~DMA_CH1_CTRL_TRIG_EN_BITS;
}
void audio_dma_resume(audio_dma_t *dma) {
// Always re-enable the non-busy channel first so it's ready to continue when the busy channel
// finishes and chains to it. (An interrupt could make the time between enables long.)
size_t first = 0;
size_t second = 1;
if (dma_channel_is_busy(dma->channel[0])) {
first = 1;
second = 0;
dma_hw->ch[dma->channel[1]].al1_ctrl |= DMA_CH1_CTRL_TRIG_EN_BITS;
dma_hw->ch[dma->channel[0]].al1_ctrl |= DMA_CH0_CTRL_TRIG_EN_BITS;
} else {
dma_hw->ch[dma->channel[0]].al1_ctrl |= DMA_CH0_CTRL_TRIG_EN_BITS;
dma_hw->ch[dma->channel[1]].al1_ctrl |= DMA_CH1_CTRL_TRIG_EN_BITS;
}
dma_hw->ch[dma->channel[first]].al1_ctrl |= DMA_CH0_CTRL_TRIG_EN_BITS;
dma_hw->ch[dma->channel[second]].al1_ctrl |= DMA_CH0_CTRL_TRIG_EN_BITS;
}
bool audio_dma_get_paused(audio_dma_t *dma) {
@ -378,6 +381,8 @@ bool audio_dma_get_playing(audio_dma_t *dma) {
// WARN(tannewt): DO NOT print from here, or anything it calls. Printing calls
// background tasks such as this and causes a stack overflow.
// NOTE(dhalbert): I successfully printed from here while debugging.
// So it's possible, but be careful.
STATIC void dma_callback_fun(void *arg) {
audio_dma_t *dma = arg;
if (dma == NULL) {

View File

@ -39,7 +39,7 @@ typedef struct {
uint8_t output_size;
uint8_t sample_spacing;
bool loop;
bool single_channel;
bool single_channel_output;
bool signed_to_unsigned;
bool unsigned_to_signed;
bool output_signed;
@ -66,16 +66,16 @@ void audio_dma_reset(void);
// This sets everything up but doesn't start the timer.
// Sample is the python object for the sample to play.
// loop is true if we should loop the sample.
// single_channel is true if we only output a single channel. When false, all channels will be
// single_channel_output is true if we only output a single channel. When false, all channels will be
// output.
// audio_channel is the index of the channel to dma. single_channel must be false in this case.
// audio_channel is the index of the channel to dma. single_channel_output must be false in this case.
// output_signed is true if the dma'd data should be signed. False and it will be unsigned.
// output_register_address is the address to copy data to.
// dma_trigger_source is the DMA trigger source which cause another copy
audio_dma_result audio_dma_setup_playback(audio_dma_t *dma,
mp_obj_t sample,
bool loop,
bool single_channel,
bool single_channel_output,
uint8_t audio_channel,
bool output_signed,
uint8_t output_resolution,

View File

@ -24,13 +24,86 @@
* THE SOFTWARE.
*/
#include "supervisor/board.h"
#include "shared-bindings/board/__init__.h"
#include "shared-bindings/displayio/FourWire.h"
#include "shared-module/displayio/__init__.h"
#include "shared-module/displayio/mipi_constants.h"
#include "shared-bindings/busio/SPI.h"
#include "shared-bindings/microcontroller/Pin.h"
#include "src/rp2_common/hardware_gpio/include/hardware/gpio.h"
#include "supervisor/shared/board.h"
displayio_fourwire_obj_t board_display_obj;
#define DELAY 0x80
uint8_t display_init_sequence[] = {
0xae, 0, // sleep
0xd5, 1, 0x80, // fOsc divide by 2
0xa8, 1, 0x3f, // multiplex 64
0xd3, 1, 0x00, // offset 0
0x40, 1, 0x00, // start line 0
0xad, 1, 0x8b, // dc/dc on
0xa1, 0, // segment remap = 0
0xc8, 0, // scan incr
0xda, 1, 0x12, // com pins
0x81, 1, 0xff, // contrast 255
0xd9, 1, 0x1f, // pre/dis-charge 2DCLKs/2CLKs
0xdb, 1, 0x20, // VCOM deslect 0.770
0x20, 1, 0x20,
0x33, 0, // VPP 9V
0xa6, 0, // not inverted
0xa4, 0, // normal
0xaf, 0, // on
};
void board_init(void) {
busio_spi_obj_t *spi = &displays[0].fourwire_bus.inline_bus;
common_hal_busio_spi_construct(spi, &pin_GPIO26, &pin_GPIO27, NULL);
common_hal_busio_spi_never_reset(spi);
displayio_fourwire_obj_t *bus = &displays[0].fourwire_bus;
bus->base.type = &displayio_fourwire_type;
common_hal_displayio_fourwire_construct(bus,
spi,
&pin_GPIO24, // Command or data
&pin_GPIO22, // Chip select
&pin_GPIO23, // Reset
1000000, // Baudrate
0, // Polarity
0); // Phase
displayio_display_obj_t *display = &displays[0].display;
display->base.type = &displayio_display_type;
common_hal_displayio_display_construct(display,
bus,
128, // Width
64, // Height
2, // column start
0, // row start
0, // rotation
1, // Color depth
true, // grayscale
false, // pixels in byte share row. Only used with depth < 8
1, // bytes per cell. Only valid for depths < 8
false, // reverse_pixels_in_byte. Only valid for depths < 8
true, // reverse_pixels_in_word
0, // Set column command
0, // Set row command
0, // Write memory command
0xd3, // set vertical scroll command
display_init_sequence,
sizeof(display_init_sequence),
NULL,
0x81,
1.0f, // brightness
false, // auto_brightness
true, // single_byte_bounds
true, // data as commands
true, // auto_refresh
60, // native_frames_per_second
true, // backlight_on_high
true); // SH1107_addressing
}
bool board_requests_safe_mode(void) {

View File

@ -1,4 +1,5 @@
#include "shared-bindings/board/__init__.h"
#include "shared-module/displayio/__init__.h"
STATIC const mp_rom_map_elem_t board_global_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_KEY1), MP_ROM_PTR(&pin_GPIO1) },
@ -15,13 +16,17 @@ STATIC const mp_rom_map_elem_t board_global_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_KEY12), MP_ROM_PTR(&pin_GPIO12) },
{ MP_ROM_QSTR(MP_QSTR_LED), MP_ROM_PTR(&pin_GPIO13) },
{ MP_ROM_QSTR(MP_QSTR_SPEAKER_SHUTDOWN), MP_ROM_PTR(&pin_GPIO14) },
{ MP_ROM_QSTR(MP_QSTR_SPEAKER), MP_ROM_PTR(&pin_GPIO16) },
{ MP_ROM_QSTR(MP_QSTR_ENCODER_SWITCH), MP_ROM_PTR(&pin_GPIO0) },
{ MP_ROM_QSTR(MP_QSTR_BUTTON), MP_ROM_PTR(&pin_GPIO0) },
{ MP_ROM_QSTR(MP_QSTR_ENCODER_A), MP_ROM_PTR(&pin_GPIO17) },
{ MP_ROM_QSTR(MP_QSTR_ROTA), MP_ROM_PTR(&pin_GPIO17) },
{ MP_ROM_QSTR(MP_QSTR_ENCODER_B), MP_ROM_PTR(&pin_GPIO18) },
{ MP_ROM_QSTR(MP_QSTR_ROTB), MP_ROM_PTR(&pin_GPIO18) },
{ MP_ROM_QSTR(MP_QSTR_NEOPIXEL), MP_ROM_PTR(&pin_GPIO19) },
@ -38,6 +43,8 @@ STATIC const mp_rom_map_elem_t board_global_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_MISO), MP_ROM_PTR(&pin_GPIO28) },
{ MP_ROM_QSTR(MP_QSTR_I2C), MP_ROM_PTR(&board_i2c_obj) },
{ MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_i2c_obj) },
{ MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) },
{ MP_ROM_QSTR(MP_QSTR_DISPLAY), MP_ROM_PTR(&displays[0].display)}
};
MP_DEFINE_CONST_DICT(board_module_globals, board_global_dict_table);

View File

@ -40,6 +40,9 @@ STATIC const mp_rom_map_elem_t board_global_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_BUZZER), MP_ROM_PTR(&pin_GPIO22) },
{ MP_ROM_QSTR(MP_QSTR_GP22), MP_ROM_PTR(&pin_GPIO22) },
{ MP_ROM_QSTR(MP_QSTR_LED), MP_ROM_PTR(&pin_GPIO25) },
{ MP_ROM_QSTR(MP_QSTR_GP25), MP_ROM_PTR(&pin_GPIO25) },
{ MP_ROM_QSTR(MP_QSTR_GP26_A0), MP_ROM_PTR(&pin_GPIO26) },
{ MP_ROM_QSTR(MP_QSTR_GP26), MP_ROM_PTR(&pin_GPIO26) },
{ MP_ROM_QSTR(MP_QSTR_A0), MP_ROM_PTR(&pin_GPIO26) },

View File

@ -145,7 +145,13 @@ void common_hal_audiobusio_i2sout_deinit(audiobusio_i2sout_obj_t *self) {
return;
}
if (common_hal_audiobusio_i2sout_get_playing(self)) {
common_hal_audiobusio_i2sout_stop(self);
}
common_hal_rp2pio_statemachine_deinit(&self->state_machine);
audio_dma_deinit(&self->dma);
}
void common_hal_audiobusio_i2sout_play(audiobusio_i2sout_obj_t *self,
@ -153,6 +159,7 @@ void common_hal_audiobusio_i2sout_play(audiobusio_i2sout_obj_t *self,
if (common_hal_audiobusio_i2sout_get_playing(self)) {
common_hal_audiobusio_i2sout_stop(self);
}
uint8_t bits_per_sample = audiosample_bits_per_sample(sample);
// Make sure we transmit a minimum of 16 bits.
// TODO: Maybe we need an intermediate object to upsample instead. This is

View File

@ -1,3 +1,4 @@
/*
* This file is part of the MicroPython project, http://micropython.org/
*
@ -36,10 +37,10 @@
// We don't bit pack because we'll only have two at most. Its better to save code size instead.
typedef struct {
mp_obj_base_t base;
bool left_justified;
rp2pio_statemachine_obj_t state_machine;
bool playing;
audio_dma_t dma;
bool left_justified;
bool playing;
} audiobusio_i2sout_obj_t;
void i2sout_reset(void);

View File

@ -46,6 +46,12 @@
#define NUM_DMA_TIMERS 4
// The PWM clock frequency is base_clock_rate / PWM_TOP, typically 125_000_000 / PWM_TOP.
// We pick BITS_PER_SAMPLE so we get a clock frequency that is above what would cause aliasing.
#define BITS_PER_SAMPLE 10
#define SAMPLE_BITS_TO_DISCARD (16 - BITS_PER_SAMPLE)
#define PWM_TOP ((1 << BITS_PER_SAMPLE) - 1)
void audiopwmout_reset() {
for (size_t i = 0; i < NUM_DMA_TIMERS; i++) {
dma_hw->timer[i] = 0;
@ -55,7 +61,10 @@ void audiopwmout_reset() {
// Caller validates that pins are free.
void common_hal_audiopwmio_pwmaudioout_construct(audiopwmio_pwmaudioout_obj_t *self,
const mcu_pin_obj_t *left_channel, const mcu_pin_obj_t *right_channel, uint16_t quiescent_value) {
if (left_channel != NULL && right_channel != NULL) {
self->stereo = right_channel != NULL;
if (self->stereo) {
if (pwm_gpio_to_slice_num(left_channel->number) != pwm_gpio_to_slice_num(right_channel->number)) {
mp_raise_ValueError(translate("Pins must share PWM slice"));
}
@ -72,22 +81,20 @@ void common_hal_audiopwmio_pwmaudioout_construct(audiopwmio_pwmaudioout_obj_t *s
// we want. ;-) We mark ourselves variable only if we're a mono output to
// prevent other PWM use on the other channel. If stereo, we say fixed
// frequency so we can allocate with ourselves.
bool mono = right_channel == NULL;
// We don't actually know our frequency yet so just pick one that shouldn't
// match anyone else. (We'll only know the frequency once we play something
// back.)
uint32_t frequency = 12500;
// We don't actually know our frequency yet. It is set when
// pwmio_pwmout_set_top() is called. This value is unimportant; it just needs to be valid.
const uint32_t frequency = 12000000;
// Make sure the PWMOut's are "deinited" by default.
self->left_pwm.pin = NULL;
self->right_pwm.pin = NULL;
pwmout_result_t result = common_hal_pwmio_pwmout_construct(&self->left_pwm,
left_channel, 0, frequency, mono);
pwmout_result_t result =
common_hal_pwmio_pwmout_construct(&self->left_pwm, left_channel, 0, frequency, !self->stereo);
if (result == PWMOUT_OK && right_channel != NULL) {
result = common_hal_pwmio_pwmout_construct(&self->right_pwm,
right_channel, 0, frequency, false);
result =
common_hal_pwmio_pwmout_construct(&self->right_pwm, right_channel, 0, frequency, false);
if (result != PWMOUT_OK) {
common_hal_pwmio_pwmout_deinit(&self->left_pwm);
}
@ -96,15 +103,16 @@ void common_hal_audiopwmio_pwmaudioout_construct(audiopwmio_pwmaudioout_obj_t *s
mp_raise_RuntimeError(translate("All timers in use"));
}
claim_pin(left_channel);
if (right_channel != NULL) {
claim_pin(right_channel);
self->quiescent_value = quiescent_value >> SAMPLE_BITS_TO_DISCARD;
common_hal_pwmio_pwmout_set_duty_cycle(&self->left_pwm, self->quiescent_value);
pwmio_pwmout_set_top(&self->left_pwm, PWM_TOP);
if (self->stereo) {
common_hal_pwmio_pwmout_set_duty_cycle(&self->right_pwm, self->quiescent_value);
pwmio_pwmout_set_top(&self->right_pwm, PWM_TOP);
}
audio_dma_init(&self->dma);
self->pacing_timer = NUM_DMA_TIMERS;
self->quiescent_value = quiescent_value;
}
bool common_hal_audiopwmio_pwmaudioout_deinited(audiopwmio_pwmaudioout_obj_t *self) {
@ -115,6 +123,7 @@ void common_hal_audiopwmio_pwmaudioout_deinit(audiopwmio_pwmaudioout_obj_t *self
if (common_hal_audiopwmio_pwmaudioout_deinited(self)) {
return;
}
if (common_hal_audiopwmio_pwmaudioout_get_playing(self)) {
common_hal_audiopwmio_pwmaudioout_stop(self);
}
@ -144,13 +153,11 @@ void common_hal_audiopwmio_pwmaudioout_play(audiopwmio_pwmaudioout_obj_t *self,
mp_raise_RuntimeError(translate("No DMA pacing timer found"));
}
uint32_t tx_register = (uint32_t)&pwm_hw->slice[self->left_pwm.slice].cc;
if (common_hal_pwmio_pwmout_deinited(&self->right_pwm)) {
// Shift the destination if we are outputting to the second PWM channel.
if (self->stereo) {
// Shift the destination if we are outputting to both PWM channels.
tx_register += self->left_pwm.channel * sizeof(uint16_t);
}
pwmio_pwmout_set_top(&self->left_pwm, 1023);
audio_dma_result result = audio_dma_setup_playback(
&self->dma,
sample,
@ -158,15 +165,16 @@ void common_hal_audiopwmio_pwmaudioout_play(audiopwmio_pwmaudioout_obj_t *self,
false, // single channel
0, // audio channel
false, // output signed
10,
(uint32_t)tx_register, // output register
BITS_PER_SAMPLE,
(uint32_t)tx_register, // output register: PWM cc register
0x3b + pacing_timer); // data request line
if (result == AUDIO_DMA_DMA_BUSY) {
// common_hal_audiobusio_i2sout_stop(self);
common_hal_audiopwmio_pwmaudioout_stop(self);
mp_raise_RuntimeError(translate("No DMA channel found"));
} else if (result == AUDIO_DMA_MEMORY_ERROR) {
// common_hal_audiobusio_i2sout_stop(self);
}
if (result == AUDIO_DMA_MEMORY_ERROR) {
common_hal_audiopwmio_pwmaudioout_stop(self);
mp_raise_RuntimeError(translate("Unable to allocate buffers for signed conversion"));
}
@ -182,6 +190,7 @@ void common_hal_audiopwmio_pwmaudioout_play(audiopwmio_pwmaudioout_obj_t *self,
// are 16-bit.
uint32_t sample_rate = audiosample_sample_rate(sample);
uint32_t system_clock = common_hal_mcu_processor_get_frequency();
uint32_t best_numerator = 0;
uint32_t best_denominator = 0;
@ -209,18 +218,27 @@ void common_hal_audiopwmio_pwmaudioout_play(audiopwmio_pwmaudioout_obj_t *self,
}
void common_hal_audiopwmio_pwmaudioout_stop(audiopwmio_pwmaudioout_obj_t *self) {
dma_hw->timer[self->pacing_timer] = 0;
self->pacing_timer = NUM_DMA_TIMERS;
if (self->pacing_timer < NUM_DMA_TIMERS) {
dma_hw->timer[self->pacing_timer] = 0;
self->pacing_timer = NUM_DMA_TIMERS;
}
audio_dma_stop(&self->dma);
// Set to quiescent level.
pwm_hw->slice[self->left_pwm.slice].cc = self->quiescent_value;
if (self->stereo) {
pwm_hw->slice[self->right_pwm.slice].cc = self->quiescent_value;
}
}
bool common_hal_audiopwmio_pwmaudioout_get_playing(audiopwmio_pwmaudioout_obj_t *self) {
bool playing = audio_dma_get_playing(&self->dma);
if (!playing && self->pacing_timer < NUM_DMA_TIMERS) {
dma_hw->timer[self->pacing_timer] = 0;
self->pacing_timer = NUM_DMA_TIMERS;
common_hal_audiopwmio_pwmaudioout_stop(self);
}
return playing;
}

View File

@ -38,6 +38,7 @@ typedef struct {
audio_dma_t dma;
uint16_t quiescent_value;
uint8_t pacing_timer;
bool stereo; // if false, only using left_pwm.
} audiopwmio_pwmaudioout_obj_t;
void audiopwmout_reset(void);

View File

@ -212,15 +212,6 @@ static bool _transfer(busio_spi_obj_t *self,
while (dma_channel_is_busy(chan_rx) || dma_channel_is_busy(chan_tx)) {
// TODO: We should idle here until we get a DMA interrupt or something else.
RUN_BACKGROUND_TASKS;
if (mp_hal_is_interrupted()) {
if (dma_channel_is_busy(chan_rx)) {
dma_channel_abort(chan_rx);
}
if (dma_channel_is_busy(chan_tx)) {
dma_channel_abort(chan_tx);
}
break;
}
}
}
@ -233,7 +224,7 @@ static bool _transfer(busio_spi_obj_t *self,
dma_channel_unclaim(chan_tx);
}
if (!use_dma && !mp_hal_is_interrupted()) {
if (!use_dma) {
// Use software for small transfers, or if couldn't claim two DMA channels
// Never have more transfers in flight than will fit into the RX FIFO,
// else FIFO will overflow if this code is heavily interrupted.
@ -241,7 +232,7 @@ static bool _transfer(busio_spi_obj_t *self,
size_t rx_remaining = len;
size_t tx_remaining = len;
while (!mp_hal_is_interrupted() && (rx_remaining || tx_remaining)) {
while (rx_remaining || tx_remaining) {
if (tx_remaining && spi_is_writable(self->peripheral) && rx_remaining - tx_remaining < fifo_depth) {
spi_get_hw(self->peripheral)->dr = (uint32_t)*data_out;
// Increment only if the buffer is the transfer length. It's 1 otherwise.

View File

@ -36,8 +36,6 @@
#include "bindings/rp2pio/StateMachine.h"
#include "common-hal/pulseio/PulseIn.h"
pulseio_pulsein_obj_t *save_self;
#define NO_PIN 0xff
#define MAX_PULSE 65535
#define MIN_PULSE 10
@ -62,7 +60,6 @@ void common_hal_pulseio_pulsein_construct(pulseio_pulsein_obj_t *self,
self->idle_state = idle_state;
self->start = 0;
self->len = 0;
save_self = self;
bool ok = rp2pio_statemachine_construct(&self->state_machine,
pulsein_program, sizeof(pulsein_program) / sizeof(pulsein_program[0]),
@ -88,7 +85,7 @@ void common_hal_pulseio_pulsein_construct(pulseio_pulsein_obj_t *self,
buf_index = 0;
pio_sm_set_in_pins(self->state_machine.pio,self->state_machine.state_machine,pin->number);
common_hal_rp2pio_statemachine_set_interrupt_handler(&(self->state_machine),&common_hal_pulseio_pulsein_interrupt,NULL,PIO_IRQ0_INTE_SM0_RXNEMPTY_BITS);
common_hal_rp2pio_statemachine_set_interrupt_handler(&(self->state_machine),&common_hal_pulseio_pulsein_interrupt,self,PIO_IRQ0_INTE_SM0_RXNEMPTY_BITS);
// exec a set pindirs to 0 for input
pio_sm_exec(self->state_machine.pio,self->state_machine.state_machine,0xe080);
@ -124,9 +121,8 @@ void common_hal_pulseio_pulsein_pause(pulseio_pulsein_obj_t *self) {
result = 0;
buf_index = 0;
}
void common_hal_pulseio_pulsein_interrupt() {
void common_hal_pulseio_pulsein_interrupt(pulseio_pulsein_obj_t *self) {
pulseio_pulsein_obj_t *self = save_self;
uint32_t rxfifo = 0;
rxfifo = pio_sm_get_blocking(self->state_machine.pio, self->state_machine.state_machine);

View File

@ -163,6 +163,8 @@ pwmout_result_t common_hal_pwmio_pwmout_construct(pwmio_pwmout_obj_t *self,
self->variable_frequency = variable_frequency;
self->duty_cycle = duty;
claim_pin(pin);
if (frequency == 0 || frequency > (common_hal_mcu_processor_get_frequency() / 2)) {
return PWMOUT_INVALID_FREQUENCY;
}

View File

@ -654,15 +654,6 @@ static bool _transfer(rp2pio_statemachine_obj_t *self,
(tx && dma_channel_is_busy(chan_tx))) {
// TODO: We should idle here until we get a DMA interrupt or something else.
RUN_BACKGROUND_TASKS;
if (mp_hal_is_interrupted()) {
if (rx && dma_channel_is_busy(chan_rx)) {
dma_channel_abort(chan_rx);
}
if (tx && dma_channel_is_busy(chan_tx)) {
dma_channel_abort(chan_tx);
}
break;
}
}
// Clear the stall bit so we can detect when the state machine is done transmitting.
self->pio->fdebug = stall_mask;
@ -677,7 +668,7 @@ static bool _transfer(rp2pio_statemachine_obj_t *self,
dma_channel_unclaim(chan_tx);
}
if (!use_dma && !mp_hal_is_interrupted()) {
if (!use_dma) {
// Use software for small transfers, or if couldn't claim two DMA channels
size_t rx_remaining = in_len / in_stride_in_bytes;
size_t tx_remaining = out_len / out_stride_in_bytes;
@ -706,9 +697,6 @@ static bool _transfer(rp2pio_statemachine_obj_t *self,
--rx_remaining;
}
RUN_BACKGROUND_TASKS;
if (mp_hal_is_interrupted()) {
break;
}
}
// Clear the stall bit so we can detect when the state machine is done transmitting.
self->pio->fdebug = stall_mask;
@ -719,9 +707,6 @@ static bool _transfer(rp2pio_statemachine_obj_t *self,
while (!pio_sm_is_tx_fifo_empty(self->pio, self->state_machine) ||
(self->wait_for_txstall && (self->pio->fdebug & stall_mask) == 0)) {
RUN_BACKGROUND_TASKS;
if (mp_hal_is_interrupted()) {
break;
}
}
}
return true;

View File

@ -21,13 +21,13 @@ CIRCUITPY_ALARM ?= 1
CIRCUITPY_RP2PIO ?= 1
CIRCUITPY_NEOPIXEL_WRITE ?= $(CIRCUITPY_RP2PIO)
CIRCUITPY_FRAMEBUFFERIO ?= 1
CIRCUITPY_FRAMEBUFFERIO ?= $(CIRCUITPY_DISPLAYIO)
CIRCUITPY_FULL_BUILD ?= 1
CIRCUITPY_AUDIOMP3 ?= 1
CIRCUITPY_BITOPS ?= 1
CIRCUITPY_IMAGECAPTURE ?= 1
CIRCUITPY_PWMIO ?= 1
CIRCUITPY_RGBMATRIX ?= 1
CIRCUITPY_RGBMATRIX ?= $(CIRCUITPY_DISPLAYIO)
CIRCUITPY_ROTARYIO ?= 1
CIRCUITPY_ROTARYIO_SOFTENCODER = 1

View File

@ -229,6 +229,9 @@ endif
ifeq ($(CIRCUITPY_PIXELBUF),1)
SRC_PATTERNS += _pixelbuf/%
endif
ifeq ($(CIRCUITPY_RAINBOW),1)
SRC_PATTERNS += rainbow/%
endif
ifeq ($(CIRCUITPY_RGBMATRIX),1)
SRC_PATTERNS += rgbmatrix/%
endif
@ -533,6 +536,7 @@ SRC_SHARED_MODULE_ALL = \
network/__init__.c \
msgpack/__init__.c \
os/__init__.c \
rainbow/__init__.c \
random/__init__.c \
rgbmatrix/RGBMatrix.c \
rgbmatrix/__init__.c \

View File

@ -644,6 +644,13 @@ extern const struct _mp_obj_module_t pwmio_module;
#define PWMIO_MODULE
#endif
#if CIRCUITPY_RAINBOW
extern const struct _mp_obj_module_t rainbow_module;
#define RAINBOW_MODULE { MP_OBJ_NEW_QSTR(MP_QSTR_rainbow), (mp_obj_t)&rainbow_module },
#else
#define RAINBOW_MODULE
#endif
#if CIRCUITPY_RANDOM
extern const struct _mp_obj_module_t random_module;
#define RANDOM_MODULE { MP_OBJ_NEW_QSTR(MP_QSTR_random), (mp_obj_t)&random_module },
@ -918,6 +925,7 @@ extern const struct _mp_obj_module_t msgpack_module;
PS2IO_MODULE \
PULSEIO_MODULE \
PWMIO_MODULE \
RAINBOW_MODULE \
RANDOM_MODULE \
RE_MODULE \
RGBMATRIX_MODULE \

View File

@ -136,9 +136,6 @@ CFLAGS += -DCIRCUITPY_DIGITALIO=$(CIRCUITPY_DIGITALIO)
CIRCUITPY_COMPUTED_GOTO_SAVE_SPACE ?= 0
CFLAGS += -DCIRCUITPY_COMPUTED_GOTO_SAVE_SPACE=$(CIRCUITPY_COMPUTED_GOTO_SAVE_SPACE)
CIRCUITPY_CONSOLE_BLE ?= 0
CFLAGS += -DCIRCUITPY_CONSOLE_BLE=$(CIRCUITPY_CONSOLE_BLE)
CIRCUITPY_CONSOLE_UART ?= 0
CFLAGS += -DCIRCUITPY_CONSOLE_UART=$(CIRCUITPY_CONSOLE_UART)
@ -249,21 +246,15 @@ CFLAGS += -DCIRCUITPY_PULSEIO=$(CIRCUITPY_PULSEIO)
CIRCUITPY_PWMIO ?= 1
CFLAGS += -DCIRCUITPY_PWMIO=$(CIRCUITPY_PWMIO)
CIRCUITPY_RAINBOW ?= 1
CFLAGS += -DCIRCUITPY_RAINBOW=$(CIRCUITPY_RAINBOW)
CIRCUITPY_RANDOM ?= 1
CFLAGS += -DCIRCUITPY_RANDOM=$(CIRCUITPY_RANDOM)
CIRCUITPY_RE ?= $(CIRCUITPY_FULL_BUILD)
CFLAGS += -DCIRCUITPY_RE=$(CIRCUITPY_RE)
CIRCUITPY_REPL_BLE ?= 0
CFLAGS += -DCIRCUITPY_REPL_BLE=$(CIRCUITPY_REPL_BLE)
CIRCUITPY_REPL_UART ?= 0
CFLAGS += -DCIRCUITPY_REPL_UART=$(CIRCUITPY_REPL_UART)
CIRCUITPY_REPL_USB ?= 1
CFLAGS += -DCIRCUITPY_REPL_USB=$(CIRCUITPY_REPL_USB)
# Should busio.I2C() check for pullups?
# Some boards in combination with certain peripherals may not want this.
CIRCUITPY_REQUIRE_I2C_PULLUPS ?= 1
@ -299,6 +290,9 @@ CFLAGS += -DCIRCUITPY_SDCARDIO=$(CIRCUITPY_SDCARDIO)
CIRCUITPY_SDIOIO ?= 0
CFLAGS += -DCIRCUITPY_SDIOIO=$(CIRCUITPY_SDIOIO)
CIRCUITPY_SERIAL_BLE ?= 0
CFLAGS += -DCIRCUITPY_SERIAL_BLE=$(CIRCUITPY_SERIAL_BLE)
CIRCUITPY_SHARPDISPLAY ?= $(CIRCUITPY_FRAMEBUFFERIO)
CFLAGS += -DCIRCUITPY_SHARPDISPLAY=$(CIRCUITPY_SHARPDISPLAY)

View File

@ -9,6 +9,7 @@ supervisor/shared/translate.h
from __future__ import print_function
import bisect
import re
import sys
@ -279,7 +280,7 @@ def translate(translation_file, i18ns):
class TextSplitter:
def __init__(self, words):
words.sort(key=lambda x: len(x), reverse=True)
words = sorted(words, key=lambda x: len(x), reverse=True)
self.words = set(words)
if words:
pat = "|".join(re.escape(w) for w in words) + "|."
@ -330,6 +331,7 @@ def compute_huffman_coding(translations, compression_filename):
end_unused = min(ord_c, end_unused)
max_words = end_unused - 0x80
bits_per_codepoint = 16 if max_ord > 255 else 8
values_type = "uint16_t" if max_ord > 255 else "uint8_t"
max_words_len = 160 if max_ord > 255 else 255
@ -344,6 +346,46 @@ def compute_huffman_coding(translations, compression_filename):
# again, neither will "there" or "wither", since they have "the"
# as substrings.
extractor = TextSplitter(words)
counter = collections.Counter()
for t in texts:
for atom in extractor.iter(t):
counter[atom] += 1
cb = huffman.codebook(counter.items())
lengths = sorted(dict((v, len(cb[k])) for k, v in counter.items()).items())
def bit_length(s):
return sum(len(cb[c]) for c in s)
def est_len(occ):
idx = bisect.bisect_left(lengths, (occ, 0))
return lengths[idx][1] + 1
# The cost of adding a dictionary word is just its storage size
# while its savings is close to the difference between the original
# huffman bit-length of the string and the estimated bit-length
# of the dictionary word, times the number of times the word appears.
#
# The savings is not strictly accurate because including a word into
# the Huffman tree bumps up the encoding lengths of all words in the
# same subtree. In the extreme case when the new word is so frequent
# that it gets a one-bit encoding, all other words will cost an extra
# bit each.
#
# Another source of inaccuracy is that compressed strings end up
# on byte boundaries, not bit boundaries, so saving 1 bit somewhere
# might not save a byte.
#
# In fact, when this change was first made, some translations (luckily,
# ones on boards not at all close to full) wasted up to 40 bytes,
# while the most constrained boards typically gained 100 bytes or
# more.
#
# The difference between the two is the estimated net savings, in bits.
def est_net_savings(s, occ):
savings = occ * (bit_length(s) - est_len(occ))
cost = len(s) * bits_per_codepoint
return savings - cost
counter = collections.Counter()
for t in texts:
for (found, word) in extractor.iter_words(t):
@ -351,16 +393,20 @@ def compute_huffman_coding(translations, compression_filename):
for substr in iter_substrings(word, minlen=3, maxlen=9):
counter[substr] += 1
# Score the candidates we found. This is an empirical formula only,
# chosen for its effectiveness.
# Score the candidates we found. This is a semi-empirical formula that
# attempts to model the number of bits saved as closely as possible.
#
# It attempts to compute the codeword lengths of the original word
# to the codeword length the dictionary entry would get, times
# the number of occurrences, less the ovehead of the entries in the
# words[] array.
scores = sorted(
((s, (len(s) - 1) ** (occ + 4)) for (s, occ) in counter.items() if occ > 4),
key=lambda x: x[1],
reverse=True,
((s, -est_net_savings(s, occ)) for (s, occ) in counter.items()), key=lambda x: x[1]
)
# Pick the one with the highest score.
if not scores:
# Pick the one with the highest score. The score must be negative.
if not scores or scores[0][-1] >= 0:
break
word = scores[0][0]

View File

@ -444,7 +444,7 @@ void mp_obj_get_complex(mp_obj_t arg, mp_float_t *real, mp_float_t *imag) {
// note: returned value in *items may point to the interior of a GC block
void mp_obj_get_array(mp_obj_t o, size_t *len, mp_obj_t **items) {
if (mp_obj_is_type(o, &mp_type_tuple)) {
if (mp_obj_is_tuple_compatible(o)) {
mp_obj_tuple_get(o, len, items);
} else if (mp_obj_is_type(o, &mp_type_list)) {
mp_obj_list_get(o, len, items);

View File

@ -764,6 +764,8 @@ extern const struct _mp_obj_exception_t mp_const_GeneratorExit_obj;
#define mp_obj_is_str_or_bytes(o) (mp_obj_is_qstr(o) || (mp_obj_is_obj(o) && ((mp_obj_base_t *)MP_OBJ_TO_PTR(o))->type->binary_op == mp_obj_str_binary_op))
#define mp_obj_is_dict_or_ordereddict(o) (mp_obj_is_obj(o) && ((mp_obj_base_t *)MP_OBJ_TO_PTR(o))->type->make_new == mp_obj_dict_make_new)
#define mp_obj_is_fun(o) (mp_obj_is_obj(o) && (((mp_obj_base_t *)MP_OBJ_TO_PTR(o))->type->name == MP_QSTR_function))
// type check is done on getiter method to allow tuple, namedtuple, attrtuple
#define mp_obj_is_tuple_compatible(o) (mp_obj_get_type(o)->getiter == mp_obj_tuple_getiter)
mp_obj_t mp_obj_new_type(qstr name, mp_obj_t bases_tuple, mp_obj_t locals_dict);
static inline mp_obj_t mp_obj_new_bool(mp_int_t x) {

View File

@ -195,6 +195,9 @@ STATIC mp_obj_t bytearray_make_new(const mp_obj_type_t *type_in, size_t n_args,
// no args: construct an empty bytearray
return MP_OBJ_FROM_PTR(array_new(BYTEARRAY_TYPECODE, 0));
} else if (mp_obj_is_int(args[0])) {
if (n_args > 1) {
mp_raise_TypeError(MP_ERROR_TEXT("wrong number of arguments"));
}
// 1 arg, an integer: construct a blank bytearray of that length
mp_uint_t len = mp_obj_get_int(args[0]);
mp_obj_array_t *o = array_new(BYTEARRAY_TYPECODE, len);

View File

@ -233,6 +233,10 @@ STATIC mp_obj_t bytes_make_new(const mp_obj_type_t *type_in, size_t n_args, cons
return MP_OBJ_FROM_PTR(o);
}
if (n_args > 1) {
goto wrong_args;
}
if (mp_obj_is_small_int(args[0])) {
mp_int_t len = MP_OBJ_SMALL_INT_VALUE(args[0]);
if (len < 0) {
@ -244,10 +248,6 @@ STATIC mp_obj_t bytes_make_new(const mp_obj_type_t *type_in, size_t n_args, cons
return mp_obj_new_str_from_vstr(&mp_type_bytes, &vstr);
}
if (n_args > 1) {
goto wrong_args;
}
// check if __bytes__ exists, and if so delegate to it
mp_obj_t dest[2];
mp_load_method_maybe(args[0], MP_QSTR___bytes__, dest);

View File

@ -34,8 +34,6 @@
#include "supervisor/shared/translate.h"
// type check is done on getiter method to allow tuple, namedtuple, attrtuple
#define mp_obj_is_tuple_compatible(o) (mp_obj_get_type(o)->getiter == mp_obj_tuple_getiter)
/******************************************************************************/
/* tuple */

View File

@ -45,7 +45,11 @@
//| ...
//|
//| def add_to_service(self, service: Service, uuid: UUID, *, properties: int = 0, read_perm: int = Attribute.OPEN, write_perm: int = Attribute.OPEN, max_length: int = 20, fixed_length: bool = False, initial_value: Optional[ReadableBuffer] = None) -> Characteristic:
//| def add_to_service(self, service: Service, uuid: UUID, *, properties: int = 0,
//| read_perm: int = Attribute.OPEN, write_perm: int = Attribute.OPEN,
//| max_length: int = 20, fixed_length: bool = False,
//| initial_value: Optional[ReadableBuffer] = None,
//| user_description: Optional[str] = None) -> Characteristic:
//| """Create a new Characteristic object, and add it to this Service.
//|
//| :param Service service: The service that will provide this characteristic
@ -65,6 +69,7 @@
//| :param bool fixed_length: True if the characteristic value is of fixed length.
//| :param ~_typing.ReadableBuffer initial_value: The initial value for this characteristic. If not given, will be
//| filled with zeros.
//| :param str user_description: User friendly description of the characteristic
//|
//| :return: the new Characteristic."""
//| ...
@ -73,7 +78,7 @@ STATIC mp_obj_t bleio_characteristic_add_to_service(size_t n_args, const mp_obj_
// class is arg[0], which we can ignore.
enum { ARG_service, ARG_uuid, ARG_properties, ARG_read_perm, ARG_write_perm,
ARG_max_length, ARG_fixed_length, ARG_initial_value };
ARG_max_length, ARG_fixed_length, ARG_initial_value, ARG_user_description };
static const mp_arg_t allowed_args[] = {
{ MP_QSTR_service, MP_ARG_REQUIRED | MP_ARG_OBJ },
{ MP_QSTR_uuid, MP_ARG_REQUIRED | MP_ARG_OBJ },
@ -83,6 +88,7 @@ STATIC mp_obj_t bleio_characteristic_add_to_service(size_t n_args, const mp_obj_
{ MP_QSTR_max_length, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_int = 20} },
{ MP_QSTR_fixed_length, MP_ARG_KW_ONLY | MP_ARG_BOOL, {.u_bool = false} },
{ MP_QSTR_initial_value, MP_ARG_KW_ONLY | MP_ARG_OBJ, {.u_obj = mp_const_none} },
{ MP_QSTR_user_description, MP_ARG_KW_ONLY | MP_ARG_OBJ, {.u_obj = mp_const_none} },
};
mp_arg_val_t args[MP_ARRAY_SIZE(allowed_args)];
@ -132,6 +138,11 @@ STATIC mp_obj_t bleio_characteristic_add_to_service(size_t n_args, const mp_obj_
mp_raise_ValueError(translate("initial_value length is wrong"));
}
const char *user_description = NULL;
if (args[ARG_user_description].u_obj != mp_const_none) {
user_description = mp_obj_str_get_str(args[ARG_user_description].u_obj);
}
bleio_characteristic_obj_t *characteristic = m_new_obj(bleio_characteristic_obj_t);
characteristic->base.type = &bleio_characteristic_type;
@ -140,7 +151,8 @@ STATIC mp_obj_t bleio_characteristic_add_to_service(size_t n_args, const mp_obj_
common_hal_bleio_characteristic_construct(
characteristic, MP_OBJ_TO_PTR(service_obj), 0, MP_OBJ_TO_PTR(uuid_obj),
properties, read_perm, write_perm,
max_length, fixed_length, &initial_value_bufinfo);
max_length, fixed_length, &initial_value_bufinfo,
user_description);
return MP_OBJ_FROM_PTR(characteristic);
}

View File

@ -44,7 +44,7 @@ extern bleio_uuid_obj_t *common_hal_bleio_characteristic_get_uuid(bleio_characte
extern size_t common_hal_bleio_characteristic_get_max_length(bleio_characteristic_obj_t *self);
extern size_t common_hal_bleio_characteristic_get_value(bleio_characteristic_obj_t *self, uint8_t *buf, size_t len);
extern void common_hal_bleio_characteristic_add_descriptor(bleio_characteristic_obj_t *self, bleio_descriptor_obj_t *descriptor);
extern void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self, bleio_service_obj_t *service, uint16_t handle, bleio_uuid_obj_t *uuid, bleio_characteristic_properties_t props, bleio_attribute_security_mode_t read_perm, bleio_attribute_security_mode_t write_perm, mp_int_t max_length, bool fixed_length, mp_buffer_info_t *initial_value_bufinfo);
extern void common_hal_bleio_characteristic_construct(bleio_characteristic_obj_t *self, bleio_service_obj_t *service, uint16_t handle, bleio_uuid_obj_t *uuid, bleio_characteristic_properties_t props, bleio_attribute_security_mode_t read_perm, bleio_attribute_security_mode_t write_perm, mp_int_t max_length, bool fixed_length, mp_buffer_info_t *initial_value_bufinfo, const char *user_description);
extern void common_hal_bleio_characteristic_set_cccd(bleio_characteristic_obj_t *self, bool notify, bool indicate);
extern void common_hal_bleio_characteristic_set_value(bleio_characteristic_obj_t *self, mp_buffer_info_t *bufinfo);

View File

@ -31,7 +31,15 @@
extern const mp_obj_type_t bleio_characteristic_buffer_type;
extern void common_hal_bleio_characteristic_buffer_construct(bleio_characteristic_buffer_obj_t *self, bleio_characteristic_obj_t *characteristic, mp_float_t timeout, size_t buffer_size);
void _common_hal_bleio_characteristic_buffer_construct(bleio_characteristic_buffer_obj_t *self,
bleio_characteristic_obj_t *characteristic,
mp_float_t timeout,
uint8_t *buffer, size_t buffer_size,
void *static_handler_entry);
void common_hal_bleio_characteristic_buffer_construct(bleio_characteristic_buffer_obj_t *self,
bleio_characteristic_obj_t *characteristic,
mp_float_t timeout,
size_t buffer_size);
uint32_t common_hal_bleio_characteristic_buffer_read(bleio_characteristic_buffer_obj_t *self, uint8_t *data, size_t len, int *errcode);
uint32_t common_hal_bleio_characteristic_buffer_rx_characters_available(bleio_characteristic_buffer_obj_t *self);
void common_hal_bleio_characteristic_buffer_clear_rx_buffer(bleio_characteristic_buffer_obj_t *self);

View File

@ -44,6 +44,6 @@ extern bleio_uuid_obj_t *common_hal_bleio_service_get_uuid(bleio_service_obj_t *
extern mp_obj_tuple_t *common_hal_bleio_service_get_characteristics(bleio_service_obj_t *self);
extern bool common_hal_bleio_service_get_is_remote(bleio_service_obj_t *self);
extern bool common_hal_bleio_service_get_is_secondary(bleio_service_obj_t *self);
extern void common_hal_bleio_service_add_characteristic(bleio_service_obj_t *self, bleio_characteristic_obj_t *characteristic, mp_buffer_info_t *initial_value_bufinfo);
extern void common_hal_bleio_service_add_characteristic(bleio_service_obj_t *self, bleio_characteristic_obj_t *characteristic, mp_buffer_info_t *initial_value_bufinfo, const char *user_description);
#endif // MICROPY_INCLUDED_SHARED_BINDINGS_BLEIO_SERVICE_H

View File

@ -3,7 +3,7 @@
*
* The MIT License (MIT)
*
* Copyright (c) 2018 Roy Hooper
* Copyright (c) 2018 Rose Hooper
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@ -44,8 +44,6 @@
#include "extmod/ulab/code/ndarray.h"
#endif
extern const int32_t colorwheel(float pos);
static void parse_byteorder(mp_obj_t byteorder_obj, pixelbuf_byteorder_details_t *parsed);
//| class PixelBuf:

View File

@ -3,7 +3,7 @@
*
* The MIT License (MIT)
*
* Copyright (c) 2018 Roy Hooper
* Copyright (c) 2018 Rose Hooper
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal

View File

@ -3,7 +3,7 @@
*
* The MIT License (MIT)
*
* Copyright (c) 2018 Roy Hooper
* Copyright (c) 2018 Rose Hooper
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@ -41,40 +41,9 @@
//| Byteorders are configured with strings, such as "RGB" or "RGBD"."""
// TODO: Pull in docs from pypixelbuf.
//| def colorwheel(n: float) -> int:
//| """C implementation of the common wheel() function found in many examples.
//| Returns the colorwheel RGB value as an integer value for n (usable in :py:class:`PixelBuf`, neopixel, and dotstar)."""
//| ...
//|
//| def wheel(n: float) -> int:
//| """Use of wheel() is deprecated. Please use colorwheel()."""
//|
STATIC mp_obj_t pixelbuf_colorwheel(mp_obj_t n) {
return MP_OBJ_NEW_SMALL_INT(colorwheel(mp_obj_is_small_int(n) ? MP_OBJ_SMALL_INT_VALUE(n) : mp_obj_get_float(n)));
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(pixelbuf_colorwheel_obj, pixelbuf_colorwheel);
const int32_t colorwheel(float pos) {
if (pos > 255) {
pos = pos - ((uint32_t)(pos / 256) * 256);
}
if (pos < 85) {
return (uint8_t)(255 - (pos * 3)) << 16 | (uint8_t)(pos * 3) << 8;
} else if (pos < 170) {
pos -= 85;
return (uint8_t)(255 - (pos * 3)) << 8 | (uint8_t)(pos * 3);
} else {
pos -= 170;
return (uint8_t)(pos * 3) << 16 | (uint8_t)(255 - (pos * 3));
}
}
STATIC const mp_rom_map_elem_t pixelbuf_module_globals_table[] = {
{ MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR__pixelbuf) },
{ MP_ROM_QSTR(MP_QSTR_PixelBuf), MP_ROM_PTR(&pixelbuf_pixelbuf_type) },
{ MP_ROM_QSTR(MP_QSTR_wheel), MP_ROM_PTR(&pixelbuf_colorwheel_obj) },
{ MP_ROM_QSTR(MP_QSTR_colorwheel), MP_ROM_PTR(&pixelbuf_colorwheel_obj) },
};
STATIC MP_DEFINE_CONST_DICT(pixelbuf_module_globals, pixelbuf_module_globals_table);

View File

@ -3,7 +3,7 @@
*
* The MIT License (MIT)
*
* Copyright (c) 2018 Roy Hooper
* Copyright (c) 2018 Rose Hooper
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@ -27,8 +27,4 @@
#ifndef CP_SHARED_BINDINGS_PIXELBUF_INIT_H
#define CP_SHARED_BINDINGS_PIXELBUF_INIT_H
#include "common-hal/digitalio/DigitalInOut.h"
const int32_t colorwheel(float pos);
#endif // CP_SHARED_BINDINGS_PIXELBUF_INIT_H

View File

@ -46,6 +46,7 @@
//|
//| """Represents a single I2C device and manages locking the bus and the device
//| address.
//|
//| :param ~busio.I2C i2c: The I2C bus the device is on
//| :param int device_address: The 7 bit device address
//| :param bool probe: Probe for the device upon object creation, default is true
@ -114,6 +115,7 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(adafruit_bus_device_i2cdevice___exit_
//| If ``start`` or ``end`` is provided, then the buffer will be sliced
//| as if ``buf[start:end]``. This will not cause an allocation like
//| ``buf[start:end]`` will so it saves memory.
//|
//| :param bytearray buf: buffer to write into
//| :param int start: Index to start writing at
//| :param int end: Index to write up to but not include; if None, use ``len(buf)``"""
@ -157,6 +159,7 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_KW(adafruit_bus_device_i2cdevice_readinto_obj, 2,
//| If ``start`` or ``end`` is provided, then the buffer will be sliced
//| as if ``buffer[start:end]``. This will not cause an allocation like
//| ``buffer[start:end]`` will so it saves memory.
//|
//| :param bytearray buf: buffer containing the bytes to write
//| :param int start: Index to start writing from
//| :param int end: Index to read up to but not include; if None, use ``len(buf)``
@ -208,6 +211,7 @@ MP_DEFINE_CONST_FUN_OBJ_KW(adafruit_bus_device_i2cdevice_write_obj, 2, adafruit_
//| will be sliced as if ``in_buffer[in_start:in_end]``. This will not
//| cause an allocation like ``in_buffer[in_start:in_end]`` will so
//| it saves memory.
//|
//| :param bytearray out_buffer: buffer containing the bytes to write
//| :param bytearray in_buffer: buffer containing the bytes to read into
//| :param int out_start: Index to start writing from

View File

@ -45,6 +45,7 @@
//|
//| """
//| Represents a single SPI device and manages locking the bus and the device address.
//|
//| :param ~busio.SPI spi: The SPI bus the device is on
//| :param ~digitalio.DigitalInOut chip_select: The chip select pin object that implements the DigitalInOut API.
//| :param int extra_clocks: The minimum number of clock cycles to cycle the bus after CS is high. (Used for SD cards.)

View File

@ -46,7 +46,7 @@
//| lines respectively.
//|
//| .. seealso:: Using this class directly requires careful lock management.
//| Instead, use :class:`~adafruit_bus_device.i2c_device.I2CDevice` to
//| Instead, use :class:`~adafruit_bus_device.I2CDevice` to
//| manage locks.
//|
//| .. seealso:: Using this class to directly read registers requires manual
@ -56,7 +56,8 @@
//| :param ~microcontroller.Pin scl: The clock pin
//| :param ~microcontroller.Pin sda: The data pin
//| :param int frequency: The clock frequency in Hertz
//| :param int timeout: The maximum clock stretching timeut - (used only for bitbangio.I2C; ignored for busio.I2C)
//| :param int timeout: The maximum clock stretching timeut - (used only for
//| :class:`bitbangio.I2C`; ignored for :class:`busio.I2C`)
//|
//| .. note:: On the nRF52840, only one I2C object may be created,
//| except on the Circuit Playground Bluefruit, which allows two,
@ -239,7 +240,7 @@ MP_DEFINE_CONST_FUN_OBJ_KW(busio_i2c_readfrom_into_obj, 3, busio_i2c_readfrom_in
//| to poll for the existence of a device.
//|
//| :param int address: 7-bit device address
//| :param ~_typing.ReadbleBuffer buffer: buffer containing the bytes to write
//| :param ~_typing.ReadableBuffer buffer: buffer containing the bytes to write
//| :param int start: Index to start writing from
//| :param int end: Index to read up to but not include. Defaults to ``len(buffer)``"""
//| ...
@ -286,12 +287,12 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_KW(busio_i2c_writeto_obj, 1, busio_i2c_writeto);
//| bit, generate a repeated start and read into ``in_buffer``. ``out_buffer`` and
//| ``in_buffer`` can be the same buffer because they are used sequentially.
//|
//| if ``start`` or ``end`` is provided, then the corresponding buffer will be sliced
//| If ``start`` or ``end`` is provided, then the corresponding buffer will be sliced
//| as if ``buffer[start:end]``. This will not cause an allocation like ``buf[start:end]``
//| will so it saves memory.
//|
//| :param int address: 7-bit device address
//| :param ~_typing.ReadbleBuffer out_buffer: buffer containing the bytes to write
//| :param ~_typing.ReadableBuffer out_buffer: buffer containing the bytes to write
//| :param ~_typing.WriteableBuffer in_buffer: buffer to write into
//| :param int out_start: Index to start writing from
//| :param int out_end: Index to read up to but not include. Defaults to ``len(buffer)``

View File

@ -65,7 +65,7 @@
//| peripherals.
//|
//| .. seealso:: Using this class directly requires careful lock management.
//| Instead, use :class:`~adafruit_bus_device.spi_device.SPIDevice` to
//| Instead, use :class:`~adafruit_bus_device.SPIDevice` to
//| manage locks.
//|
//| .. seealso:: Using this class to directly read registers requires manual

View File

@ -54,7 +54,7 @@
//| Most people should not use this class directly. Use a specific display driver instead that will
//| contain the initialization sequence at minimum."""
//|
//| def __init__(self, display_bus: _DisplayBus, init_sequence: ReadableBuffer, *, width: int, height: int, colstart: int = 0, rowstart: int = 0, rotation: int = 0, color_depth: int = 16, grayscale: bool = False, pixels_in_byte_share_row: bool = True, bytes_per_cell: int = 1, reverse_pixels_in_byte: bool = False, set_column_command: int = 0x2a, set_row_command: int = 0x2b, write_ram_command: int = 0x2c, set_vertical_scroll: int = 0, backlight_pin: Optional[microcontroller.Pin] = None, brightness_command: Optional[int] = None, brightness: float = 1.0, auto_brightness: bool = False, single_byte_bounds: bool = False, data_as_commands: bool = False, auto_refresh: bool = True, native_frames_per_second: int = 60) -> None:
//| def __init__(self, display_bus: _DisplayBus, init_sequence: ReadableBuffer, *, width: int, height: int, colstart: int = 0, rowstart: int = 0, rotation: int = 0, color_depth: int = 16, grayscale: bool = False, pixels_in_byte_share_row: bool = True, bytes_per_cell: int = 1, reverse_pixels_in_byte: bool = False, set_column_command: int = 0x2a, set_row_command: int = 0x2b, write_ram_command: int = 0x2c, set_vertical_scroll: int = 0, backlight_pin: Optional[microcontroller.Pin] = None, brightness_command: Optional[int] = None, brightness: float = 1.0, auto_brightness: bool = False, single_byte_bounds: bool = False, data_as_commands: bool = False, auto_refresh: bool = True, native_frames_per_second: int = 60, backlight_on_high: bool = True, SH1107_addressing: bool = False) -> None:
//| r"""Create a Display object on the given display bus (`FourWire`, `ParallelBus` or `I2CDisplay`).
//|
//| The ``init_sequence`` is bitpacked to minimize the ram impact. Every command begins with a
@ -107,10 +107,11 @@
//| :param bool auto_brightness: If True, brightness is controlled via an ambient light sensor or other mechanism.
//| :param bool single_byte_bounds: Display column and row commands use single bytes
//| :param bool data_as_commands: Treat all init and boundary data as SPI commands. Certain displays require this.
//| :param bool SH1107_addressing: Special quirk for SH1107, use upper/lower column set and page set
//| :param bool auto_refresh: Automatically refresh the screen
//| :param int native_frames_per_second: Number of display refreshes per second that occur with the given init_sequence.
//| :param bool backlight_on_high: If True, pulling the backlight pin high turns the backlight on."""
//| :param bool backlight_on_high: If True, pulling the backlight pin high turns the backlight on.
//| :param bool SH1107_addressing: Special quirk for SH1107, use upper/lower column set and page set
//| """
//| ...
//|
STATIC mp_obj_t displayio_display_make_new(const mp_obj_type_t *type, size_t n_args,

View File

@ -56,7 +56,7 @@
//| tile_width and tile_height match the height of the bitmap by default.
//|
//| :param Bitmap bitmap: The bitmap storing one or more tiles.
//| :param ColorConverter or Palette pixel_shader: The pixel shader that produces colors from values
//| :param ColorConverter,Palette pixel_shader: The pixel shader that produces colors from values
//| :param int width: Width of the grid in tiles.
//| :param int height: Height of the grid in tiles.
//| :param int tile_width: Width of a single tile in pixels. Defaults to the full Bitmap and must evenly divide into the Bitmap's dimensions.

View File

@ -70,6 +70,10 @@ MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, RGB565, DISPLAY
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, RGB565_SWAPPED, DISPLAYIO_COLORSPACE_RGB565_SWAPPED);
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, RGB555, DISPLAYIO_COLORSPACE_RGB555);
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, RGB555_SWAPPED, DISPLAYIO_COLORSPACE_RGB555_SWAPPED);
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, BGR565, DISPLAYIO_COLORSPACE_BGR565);
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, BGR565_SWAPPED, DISPLAYIO_COLORSPACE_BGR565_SWAPPED);
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, BGR555, DISPLAYIO_COLORSPACE_BGR555);
MAKE_ENUM_VALUE(displayio_colorspace_type, displayio_colorspace, BGR555_SWAPPED, DISPLAYIO_COLORSPACE_BGR555_SWAPPED);
//| class Colorspace:
//| """The colorspace for a `ColorConverter` to operate in"""
@ -95,6 +99,10 @@ MAKE_ENUM_MAP(displayio_colorspace) {
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, RGB565_SWAPPED),
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, RGB555),
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, RGB555_SWAPPED),
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, BGR565),
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, BGR565_SWAPPED),
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, BGR555),
MAKE_ENUM_MAP_ENTRY(displayio_colorspace, BGR555_SWAPPED),
};
STATIC MP_DEFINE_CONST_DICT(displayio_colorspace_locals_dict, displayio_colorspace_locals_table);

View File

@ -46,6 +46,10 @@ typedef enum {
DISPLAYIO_COLORSPACE_RGB555,
DISPLAYIO_COLORSPACE_RGB565_SWAPPED,
DISPLAYIO_COLORSPACE_RGB555_SWAPPED,
DISPLAYIO_COLORSPACE_BGR565,
DISPLAYIO_COLORSPACE_BGR555,
DISPLAYIO_COLORSPACE_BGR565_SWAPPED,
DISPLAYIO_COLORSPACE_BGR555_SWAPPED,
} displayio_colorspace_t;
typedef bool (*display_bus_bus_reset)(mp_obj_t bus);

View File

@ -237,7 +237,7 @@ const mp_obj_property_t pulseio_pulsein_paused_obj = {
//| def __bool__(self) -> bool: ...
//|
//| def __len__(self) -> int:
//| """Returns the current pulse length
//| """Returns the number of pulse durations currently stored.
//|
//| This allows you to::
//|

View File

@ -0,0 +1,54 @@
/*
* This file is part of the CircuitPython project, https://github.com/adafruit/circuitpython
*
* The MIT License (MIT)
*
* Copyright (c) 2021 Kattni Rembor
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#include "shared-bindings/rainbow/__init__.h"
#include "py/mpconfig.h"
#include "py/obj.h"
//| """`rainbow` module.
//|
//| Provides the `colorwheel()` function."""
//|
//| def colorwheel(n: float) -> int:
//| """C implementation of the common colorwheel() function found in many examples.
//| Returns the colorwheel RGB value as an integer value for n (usable in neopixel and dotstar)."""
//| ...
//|
STATIC mp_obj_t rainbow_colorwheel(mp_obj_t n) {
return MP_OBJ_NEW_SMALL_INT(colorwheel(mp_obj_is_small_int(n) ? MP_OBJ_SMALL_INT_VALUE(n) : mp_obj_get_float(n)));
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(rainbow_colorwheel_obj, rainbow_colorwheel);
STATIC const mp_rom_map_elem_t rainbow_module_globals_table[] = {
{ MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR_rainbow) },
{ MP_ROM_QSTR(MP_QSTR_colorwheel), MP_ROM_PTR(&rainbow_colorwheel_obj) },
};
STATIC MP_DEFINE_CONST_DICT(rainbow_module_globals, rainbow_module_globals_table);
const mp_obj_module_t rainbow_module = {
.base = { &mp_type_module },
.globals = (mp_obj_dict_t *)&rainbow_module_globals,
};

View File

@ -0,0 +1,33 @@
/*
* This file is part of the CircuitPython project, https://github.com/adafruit/circuitpython
*
* The MIT License (MIT)
*
* Copyright (c) 2021 Kattni Rembor
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#ifndef CP_SHARED_BINDINGS_RAINBOW_INIT_H
#define CP_SHARED_BINDINGS_RAINBOW_INIT_H
#include <stdint.h>
const int32_t colorwheel(float pos);
#endif // CP_SHARED_BINDINGS_RAINBOW_INIT_H

View File

@ -80,22 +80,21 @@ MP_DEFINE_CONST_FUN_OBJ_1(time_sleep_obj, time_sleep);
#if MICROPY_PY_COLLECTIONS
mp_obj_t struct_time_make_new(const mp_obj_type_t *type, size_t n_args, const mp_obj_t *args, mp_map_t *kw_args) {
if (n_args != 1 || (kw_args != NULL && kw_args->used > 0)) {
return namedtuple_make_new(type, n_args, args, kw_args);
}
if (mp_obj_get_type(args[0])->getiter != mp_obj_tuple_getiter || ((mp_obj_tuple_t *)MP_OBJ_TO_PTR(args[0]))->len != 9) {
mp_arg_check_num(n_args, kw_args, 1, 1, false);
size_t len;
mp_obj_t *items;
mp_obj_get_array(args[0], &len, &items);
if (len != 9) {
mp_raise_TypeError(translate("time.struct_time() takes a 9-sequence"));
}
mp_obj_tuple_t *tuple = MP_OBJ_TO_PTR(args[0]);
return namedtuple_make_new(type, 9, tuple->items, NULL);
return namedtuple_make_new(type, len, items, NULL);
}
//| class struct_time:
//| def __init__(self, time_tuple: Tuple[int, int, int, int, int, int, int, int, int]) -> None:
//| """Structure used to capture a date and time. Note that it takes a tuple!
//| def __init__(self, time_tuple: Sequence[int]) -> None:
//| """Structure used to capture a date and time. Can be constructed from a `struct_time`, `tuple`, `list`, or `namedtuple` with 9 elements.
//|
//| :param tuple time_tuple: Tuple of time info: ``(tm_year, tm_mon, tm_mday, tm_hour, tm_min, tm_sec, tm_wday, tm_yday, tm_isdst)``
//| :param Sequence time_tuple: Sequence of time info: ``(tm_year, tm_mon, tm_mday, tm_hour, tm_min, tm_sec, tm_wday, tm_yday, tm_isdst)``
//|
//| * ``tm_year``: the year, 2017 for example
//| * ``tm_mon``: the month, range [1, 12]

View File

@ -3,7 +3,7 @@
*
* The MIT License (MIT)
*
* Copyright (c) 2018 Roy Hooper
* Copyright (c) 2018 Rose Hooper
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal

Some files were not shown because too many files have changed in this diff Show More