Buffer sequential writes

dv_stick
Mike Bell 2023-05-17 20:45:26 +01:00 zatwierdzone przez Phil Howard
rodzic f4b8bc9025
commit a1caa9495c
4 zmienionych plików z 61 dodań i 37 usunięć

Wyświetl plik

@ -98,6 +98,13 @@ namespace pimoroni {
}
void APS6404::write(uint32_t addr, uint32_t* data, uint32_t len_in_bytes) {
dma_channel_config c = dma_channel_get_default_config(dma_channel);
channel_config_set_read_increment(&c, true);
channel_config_set_write_increment(&c, false);
channel_config_set_dreq(&c, pio_get_dreq(pio, pio_sm, true));
channel_config_set_transfer_data_size(&c, DMA_SIZE_32);
channel_config_set_bswap(&c, true);
if (!last_cmd_was_write) {
wait_for_finish_blocking();
setup_cmd_buffer_dma(true);
@ -114,13 +121,6 @@ namespace pimoroni {
pio_sm_put_blocking(pio, pio_sm, 0x38000000u | addr);
pio_sm_put_blocking(pio, pio_sm, pio_offset + sram_offset_do_write);
dma_channel_config c = dma_channel_get_default_config(dma_channel);
channel_config_set_read_increment(&c, true);
channel_config_set_write_increment(&c, false);
channel_config_set_dreq(&c, pio_get_dreq(pio, pio_sm, true));
channel_config_set_transfer_data_size(&c, DMA_SIZE_32);
channel_config_set_bswap(&c, true);
dma_channel_configure(
dma_channel, &c,
&pio->txf[pio_sm],
@ -132,6 +132,13 @@ namespace pimoroni {
}
void APS6404::write_repeat(uint32_t addr, uint32_t data, uint32_t len_in_bytes) {
dma_channel_config c = dma_channel_get_default_config(dma_channel);
channel_config_set_read_increment(&c, false);
channel_config_set_write_increment(&c, false);
channel_config_set_dreq(&c, pio_get_dreq(pio, pio_sm, true));
channel_config_set_transfer_data_size(&c, DMA_SIZE_32);
channel_config_set_bswap(&c, true);
if (!last_cmd_was_write) {
wait_for_finish_blocking();
setup_cmd_buffer_dma(true);
@ -149,13 +156,6 @@ namespace pimoroni {
pio_sm_put_blocking(pio, pio_sm, 0x38000000u | addr);
pio_sm_put_blocking(pio, pio_sm, pio_offset + sram_offset_do_write);
dma_channel_config c = dma_channel_get_default_config(dma_channel);
channel_config_set_read_increment(&c, false);
channel_config_set_write_increment(&c, false);
channel_config_set_dreq(&c, pio_get_dreq(pio, pio_sm, true));
channel_config_set_transfer_data_size(&c, DMA_SIZE_32);
channel_config_set_bswap(&c, true);
dma_channel_configure(
dma_channel, &c,
&pio->txf[pio_sm],
@ -199,9 +199,6 @@ namespace pimoroni {
}
void APS6404::start_read(uint32_t* read_buf, uint32_t total_len_in_words, int chain_channel) {
last_cmd_was_write = false;
wait_for_finish_blocking();
dma_channel_config c = dma_channel_get_default_config(dma_channel);
channel_config_set_read_increment(&c, false);
channel_config_set_write_increment(&c, true);
@ -212,6 +209,9 @@ namespace pimoroni {
channel_config_set_chain_to(&c, chain_channel);
}
last_cmd_was_write = false;
wait_for_finish_blocking();
dma_channel_configure(
dma_channel, &c,
read_buf,

Wyświetl plik

@ -16,6 +16,7 @@ namespace pimoroni {
gpio_init(VSYNC);
gpio_set_dir(VSYNC, GPIO_IN);
sleep_ms(200);
swd_load_program(section_addresses, section_data, section_data_len, sizeof(section_addresses) / sizeof(section_addresses[0]), 0x20000001, 0x15004000, true);
ram.init();
@ -27,7 +28,7 @@ namespace pimoroni {
bank = 0;
gpio_put(RAM_SEL, 0);
sleep_ms(500);
sleep_ms(100);
printf("Start I2C\n");
//i2c_init(i2c0, 100000);
@ -41,26 +42,16 @@ namespace pimoroni {
}
void DVDisplay::flip() {
if (pixel_buffer_location.y != -1) {
ram.write(pointToAddress(pixel_buffer_location), pixel_buffer, pixel_buffer_x << 1);
pixel_buffer_location.y = -1;
}
bank ^= 1;
ram.wait_for_finish_blocking();
while (gpio_get(VSYNC) == 0);
gpio_put(RAM_SEL, bank);
}
void DVDisplay::write(uint32_t address, size_t len, const uint16_t *data)
{
if ((uintptr_t)data & 2) {
write(address, 1, *data);
data++;
len--;
address += 2;
}
if (len > 0) {
ram.write(address, (uint32_t*)data, len << 1);
}
}
void DVDisplay::write(uint32_t address, size_t len, const uint16_t colour)
{
uint32_t val = colour | ((uint32_t)colour << 16);
@ -75,7 +66,21 @@ namespace pimoroni {
void DVDisplay::write_pixel(const Point &p, uint16_t colour)
{
write(pointToAddress(p), 1, colour);
if (pixel_buffer_location.y == p.y && pixel_buffer_location.x + pixel_buffer_x == p.x) {
if (pixel_buffer_x & 1) pixel_buffer[pixel_buffer_x >> 1] |= (uint32_t)colour << 16;
else pixel_buffer[pixel_buffer_x >> 1] = colour;
if (++pixel_buffer_x == PIXEL_BUFFER_LEN_IN_WORDS * 2) {
ram.write(pointToAddress(pixel_buffer_location), pixel_buffer, PIXEL_BUFFER_LEN_IN_WORDS * 4);
pixel_buffer_location.y = -1;
}
return;
}
else if (pixel_buffer_location.y != -1) {
ram.write(pointToAddress(pixel_buffer_location), pixel_buffer, pixel_buffer_x << 1);
}
pixel_buffer_location = p;
pixel_buffer_x = 1;
pixel_buffer[0] = colour;
}
void DVDisplay::write_pixel_span(const Point &p, uint l, uint16_t colour)

Wyświetl plik

@ -48,6 +48,7 @@ namespace pimoroni {
: ram(CS, D0)
, i2c(I2C_SDA, I2C_SCL)
, width(width), height(height)
, pixel_buffer_location(-1, -1)
{}
//--------------------------------------------------
@ -66,7 +67,7 @@ namespace pimoroni {
for(uint k = 0; k < 1024*mb; k++) {
sprintf(writeBuffer, "%u-%u", b, k);
write(k*1024, strlen(writeBuffer)+1, (uint16_t *)writeBuffer);
ram.write(k*1024, (uint32_t *)writeBuffer, strlen(writeBuffer)+1);
}
}
@ -91,8 +92,12 @@ namespace pimoroni {
void flip();
private:
void write(uint32_t address, size_t len, const uint16_t *data);
void write(uint32_t address, size_t len, const uint16_t byte);
static constexpr int PIXEL_BUFFER_LEN_IN_WORDS = 16;
uint32_t pixel_buffer[PIXEL_BUFFER_LEN_IN_WORDS];
Point pixel_buffer_location;
int32_t pixel_buffer_x;
void write(uint32_t address, size_t len, const uint16_t colour);
void read(uint32_t address, size_t len, uint16_t *data);
void write_header(uint bank);

Wyświetl plik

@ -39,7 +39,7 @@ int main() {
gpio_set_dir(BUTTON_A, GPIO_IN);
gpio_pull_up(BUTTON_A);
sleep_ms(5000);
//sleep_ms(5000);
DVDisplay display(FRAME_WIDTH, FRAME_HEIGHT);
display.init();
@ -79,6 +79,20 @@ int main() {
graphics.set_pen(0xFFFF);
graphics.clear();
for (uint i = 0; i < 128; i++) {
for (uint j = 0; j < 256; j++) {
graphics.set_pen((j << 7) | i);
graphics.pixel(Point(j, i));
}
}
for (uint i = 0; i < 128; i++) {
for (uint j = 0; j < 256; j++) {
graphics.set_pen((j << 7) | i);
graphics.pixel(Point(i, j+128));
}
}
for(int i =0 ; i < NUM_CIRCLES ; i++)
{
graphics.set_pen(0);