/*
 * QEMU DM163 8x3-channel constant current led driver
 * driving columns of associated 8x8 RGB matrix.
 *
 * Copyright (C) 2024 Samuel Tardieu <sam@rfc1149.net>
 * Copyright (C) 2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
 * Copyright (C) 2024 Inès Varhol <ines.varhol@telecom-paris.fr>
 *
 * SPDX-License-Identifier: GPL-2.0-or-later
 */

/*
 * The reference used for the DM163 is the following :
 * http://www.siti.com.tw/product/spec/LED/DM163.pdf
 */

#include "qemu/osdep.h"
#include "qapi/error.h"
#include "migration/vmstate.h"
#include "hw/irq.h"
#include "hw/qdev-properties.h"
#include "hw/display/dm163.h"
#include "ui/console.h"
#include "trace.h"

#define LED_SQUARE_SIZE 100
/* Number of frames a row stays visible after being turned off. */
#define ROW_PERSISTENCE 3
#define TURNED_OFF_ROW (COLOR_BUFFER_SIZE - 1)

static const VMStateDescription vmstate_dm163 = {
    .name = TYPE_DM163,
    .version_id = 1,
    .minimum_version_id = 1,
    .fields = (const VMStateField[]) {
        VMSTATE_UINT64_ARRAY(bank0_shift_register, DM163State, 3),
        VMSTATE_UINT64_ARRAY(bank1_shift_register, DM163State, 3),
        VMSTATE_UINT16_ARRAY(latched_outputs, DM163State, DM163_NUM_LEDS),
        VMSTATE_UINT16_ARRAY(outputs, DM163State, DM163_NUM_LEDS),
        VMSTATE_UINT8(dck, DM163State),
        VMSTATE_UINT8(en_b, DM163State),
        VMSTATE_UINT8(lat_b, DM163State),
        VMSTATE_UINT8(rst_b, DM163State),
        VMSTATE_UINT8(selbk, DM163State),
        VMSTATE_UINT8(sin, DM163State),
        VMSTATE_UINT8(activated_rows, DM163State),
        VMSTATE_UINT32_2DARRAY(buffer, DM163State, COLOR_BUFFER_SIZE,
                               RGB_MATRIX_NUM_COLS),
        VMSTATE_UINT8(last_buffer_idx, DM163State),
        VMSTATE_UINT8_ARRAY(buffer_idx_of_row, DM163State, RGB_MATRIX_NUM_ROWS),
        VMSTATE_UINT8_ARRAY(row_persistence_delay, DM163State,
                            RGB_MATRIX_NUM_ROWS),
        VMSTATE_END_OF_LIST()
    }
};

static void dm163_reset_hold(Object *obj, ResetType type)
{
    DM163State *s = DM163(obj);

    s->sin = 0;
    s->dck = 0;
    s->rst_b = 0;
    /* Ensuring the first falling edge of lat_b isn't missed */
    s->lat_b = 1;
    s->selbk = 0;
    s->en_b = 0;
    /* Reset stops the PWM, not the shift and latched registers. */
    memset(s->outputs, 0, sizeof(s->outputs));

    s->activated_rows = 0;
    s->redraw = 0;
    trace_dm163_redraw(s->redraw);
    for (unsigned i = 0; i < COLOR_BUFFER_SIZE; i++) {
        memset(s->buffer[i], 0, sizeof(s->buffer[0]));
    }
    s->last_buffer_idx = 0;
    memset(s->buffer_idx_of_row, TURNED_OFF_ROW, sizeof(s->buffer_idx_of_row));
    memset(s->row_persistence_delay, 0, sizeof(s->row_persistence_delay));
}

static void dm163_dck_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    if (new_state && !s->dck) {
        /*
         * On raising dck, sample selbk to get the bank to use, and
         * sample sin for the bit to enter into the bank shift buffer.
         */
        uint64_t *sb =
            s->selbk ? s->bank1_shift_register : s->bank0_shift_register;
        /* Output the outgoing bit on sout */
        const bool sout = (s->selbk ? sb[2] & MAKE_64BIT_MASK(63, 1) :
                           sb[2] & MAKE_64BIT_MASK(15, 1)) != 0;
        qemu_set_irq(s->sout, sout);
        /* Enter sin into the shift buffer */
        sb[2] = (sb[2] << 1) | ((sb[1] >> 63) & 1);
        sb[1] = (sb[1] << 1) | ((sb[0] >> 63) & 1);
        sb[0] = (sb[0] << 1) | s->sin;
    }

    s->dck = new_state;
    trace_dm163_dck(new_state);
}

static void dm163_propagate_outputs(DM163State *s)
{
    s->last_buffer_idx = (s->last_buffer_idx + 1) % RGB_MATRIX_NUM_ROWS;
    /* Values are output when reset is high and enable is low. */
    if (s->rst_b && !s->en_b) {
        memcpy(s->outputs, s->latched_outputs, sizeof(s->outputs));
    } else {
        memset(s->outputs, 0, sizeof(s->outputs));
    }
    for (unsigned x = 0; x < RGB_MATRIX_NUM_COLS; x++) {
        /* Grouping the 3 RGB channels in a pixel value */
        const uint16_t b = extract16(s->outputs[3 * x + 0], 6, 8);
        const uint16_t g = extract16(s->outputs[3 * x + 1], 6, 8);
        const uint16_t r = extract16(s->outputs[3 * x + 2], 6, 8);
        uint32_t rgba = 0;

        trace_dm163_channels(3 * x + 2, r);
        trace_dm163_channels(3 * x + 1, g);
        trace_dm163_channels(3 * x + 0, b);

        rgba = deposit32(rgba,  0, 8, r);
        rgba = deposit32(rgba,  8, 8, g);
        rgba = deposit32(rgba, 16, 8, b);

        /* Led values are sent from the last one to the first one */
        s->buffer[s->last_buffer_idx][RGB_MATRIX_NUM_COLS - x - 1] = rgba;
    }
    for (unsigned row = 0; row < RGB_MATRIX_NUM_ROWS; row++) {
        if (s->activated_rows & (1 << row)) {
            s->buffer_idx_of_row[row] = s->last_buffer_idx;
            s->redraw |= (1 << row);
            trace_dm163_redraw(s->redraw);
        }
    }
}

static void dm163_en_b_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    s->en_b = new_state;
    dm163_propagate_outputs(s);
    trace_dm163_en_b(new_state);
}

static uint8_t dm163_bank0(const DM163State *s, uint8_t led)
{
    /*
     * Bank 0 uses 6 bits per led, so a value may be stored accross
     * two uint64_t entries.
     */
    const uint8_t low_bit = 6 * led;
    const uint8_t low_word = low_bit / 64;
    const uint8_t high_word = (low_bit + 5) / 64;
    const uint8_t low_shift = low_bit % 64;

    if (low_word == high_word) {
        /* Simple case: the value belongs to one entry. */
        return extract64(s->bank0_shift_register[low_word], low_shift, 6);
    }

    const uint8_t nb_bits_in_low_word = 64 - low_shift;
    const uint8_t nb_bits_in_high_word = 6 - nb_bits_in_low_word;

    const uint64_t bits_in_low_word = \
        extract64(s->bank0_shift_register[low_word], low_shift,
                  nb_bits_in_low_word);
    const uint64_t bits_in_high_word = \
        extract64(s->bank0_shift_register[high_word], 0,
                  nb_bits_in_high_word);
    uint8_t val = 0;

    val = deposit32(val, 0, nb_bits_in_low_word, bits_in_low_word);
    val = deposit32(val, nb_bits_in_low_word, nb_bits_in_high_word,
                    bits_in_high_word);

    return val;
}

static uint8_t dm163_bank1(const DM163State *s, uint8_t led)
{
    const uint64_t entry = s->bank1_shift_register[led / RGB_MATRIX_NUM_COLS];
    return extract64(entry, 8 * (led % RGB_MATRIX_NUM_COLS), 8);
}

static void dm163_lat_b_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    if (s->lat_b && !new_state) {
        for (int led = 0; led < DM163_NUM_LEDS; led++) {
            s->latched_outputs[led] = dm163_bank0(s, led) * dm163_bank1(s, led);
        }
        dm163_propagate_outputs(s);
    }

    s->lat_b = new_state;
    trace_dm163_lat_b(new_state);
}

static void dm163_rst_b_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    s->rst_b = new_state;
    dm163_propagate_outputs(s);
    trace_dm163_rst_b(new_state);
}

static void dm163_selbk_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    s->selbk = new_state;
    trace_dm163_selbk(new_state);
}

static void dm163_sin_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    s->sin = new_state;
    trace_dm163_sin(new_state);
}

static void dm163_rows_gpio_handler(void *opaque, int line, int new_state)
{
    DM163State *s = opaque;

    if (new_state) {
        s->activated_rows |= (1 << line);
        s->buffer_idx_of_row[line] = s->last_buffer_idx;
        s->redraw |= (1 << line);
        trace_dm163_redraw(s->redraw);
    } else {
        s->activated_rows &= ~(1 << line);
        s->row_persistence_delay[line] = ROW_PERSISTENCE;
    }
    trace_dm163_activated_rows(s->activated_rows);
}

static void dm163_invalidate_display(void *opaque)
{
    DM163State *s = (DM163State *)opaque;
    s->redraw = 0xFF;
    trace_dm163_redraw(s->redraw);
}

static void update_row_persistence_delay(DM163State *s, unsigned row)
{
    if (s->row_persistence_delay[row]) {
        s->row_persistence_delay[row]--;
    } else {
        /*
         * If the ROW_PERSISTENCE delay is up,
         * the row is turned off.
         */
        s->buffer_idx_of_row[row] = TURNED_OFF_ROW;
        s->redraw |= (1 << row);
        trace_dm163_redraw(s->redraw);
    }
}

static uint32_t *update_display_of_row(DM163State *s, uint32_t *dest,
                                       unsigned row)
{
    for (unsigned _ = 0; _ < LED_SQUARE_SIZE; _++) {
        for (int x = 0; x < RGB_MATRIX_NUM_COLS * LED_SQUARE_SIZE; x++) {
            /* UI layer guarantees that there's 32 bits per pixel (Mar 2024) */
            *dest++ = s->buffer[s->buffer_idx_of_row[row]][x / LED_SQUARE_SIZE];
        }
    }

    dpy_gfx_update(s->console, 0, LED_SQUARE_SIZE * row,
                    RGB_MATRIX_NUM_COLS * LED_SQUARE_SIZE, LED_SQUARE_SIZE);
    s->redraw &= ~(1 << row);
    trace_dm163_redraw(s->redraw);

    return dest;
}

static void dm163_update_display(void *opaque)
{
    DM163State *s = (DM163State *)opaque;
    DisplaySurface *surface = qemu_console_surface(s->console);
    uint32_t *dest;

    dest = surface_data(surface);
    for (unsigned row = 0; row < RGB_MATRIX_NUM_ROWS; row++) {
        update_row_persistence_delay(s, row);
        if (!extract8(s->redraw, row, 1)) {
            dest += LED_SQUARE_SIZE * LED_SQUARE_SIZE * RGB_MATRIX_NUM_COLS;
            continue;
        }
        dest = update_display_of_row(s, dest, row);
    }
}

static const GraphicHwOps dm163_ops = {
    .invalidate  = dm163_invalidate_display,
    .gfx_update  = dm163_update_display,
};

static void dm163_realize(DeviceState *dev, Error **errp)
{
    DM163State *s = DM163(dev);

    qdev_init_gpio_in(dev, dm163_rows_gpio_handler, RGB_MATRIX_NUM_ROWS);
    qdev_init_gpio_in(dev, dm163_sin_gpio_handler, 1);
    qdev_init_gpio_in(dev, dm163_dck_gpio_handler, 1);
    qdev_init_gpio_in(dev, dm163_rst_b_gpio_handler, 1);
    qdev_init_gpio_in(dev, dm163_lat_b_gpio_handler, 1);
    qdev_init_gpio_in(dev, dm163_selbk_gpio_handler, 1);
    qdev_init_gpio_in(dev, dm163_en_b_gpio_handler, 1);
    qdev_init_gpio_out_named(dev, &s->sout, "sout", 1);

    s->console = graphic_console_init(dev, 0, &dm163_ops, s);
    qemu_console_resize(s->console, RGB_MATRIX_NUM_COLS * LED_SQUARE_SIZE,
                        RGB_MATRIX_NUM_ROWS * LED_SQUARE_SIZE);
}

static void dm163_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *dc = DEVICE_CLASS(klass);
    ResettableClass *rc = RESETTABLE_CLASS(klass);

    dc->desc = "DM163";
    dc->vmsd = &vmstate_dm163;
    dc->realize = dm163_realize;
    rc->phases.hold = dm163_reset_hold;
    set_bit(DEVICE_CATEGORY_DISPLAY, dc->categories);
}

static const TypeInfo dm163_types[] = {
    {
        .name = TYPE_DM163,
        .parent = TYPE_DEVICE,
        .instance_size = sizeof(DM163State),
        .class_init = dm163_class_init
    }
};

DEFINE_TYPES(dm163_types)
