about summary refs log tree commit diff stats
path: root/003trace.test.cc
Commit message (Expand)AuthorAgeFilesLines
* 3547Kartik K. Agaram2016-10-221-1/+0
* 3294Kartik K. Agaram2016-09-021-3/+3
* 3267Kartik K. Agaram2016-08-281-2/+0
* 2547Kartik K. Agaram2015-12-241-0/+6
* 2258 - separate warnings from errorsKartik K. Agaram2015-10-061-4/+4
* 1844 - explicitly end each trace lineKartik K. Agaram2015-07-251-17/+17
* 1669 - now it fails in the right placeKartik K. Agaram2015-06-271-0/+5
* 1414 - traces now robust to new recipes/typesKartik K. Agaram2015-05-211-0/+21
* 1413Kartik K. Agaram2015-05-211-39/+12
* 1412 - starting to clean up trace formatKartik K. Agaram2015-05-211-47/+0
* 1299 - stop using [] in any vectorKartik K. Agaram2015-05-071-10/+10
* 1276 - make C++ version the defaultKartik K. Agaram2015-05-051-0/+169
131'>131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153
#include "tty.h"
#include "alloc.h"

Tty* createTty(uint16 lineCount, uint16 columnCount, TtyFlushScreenFunction flushFunction) {
    Tty* tty = kmalloc(sizeof(Tty));
    memset((uint8*)tty, 0, sizeof(Tty));

    tty->lineCount = lineCount;
    tty->columnCount = columnCount;
    tty->buffer = kmalloc(tty->lineCount * tty->columnCount * 2);
    tty->currentColumn = 0;
    tty->currentLine = 0;
    tty->color = 0x0A;

    memset(tty->lineBuffer, 0, TTY_LINEBUFFER_SIZE);
    tty->lineBufferIndex = 0;
    tty->keyBuffer = FifoBuffer_create(64);
    tty->flushScreen = flushFunction;

    tty->term.c_cc[VMIN] = 1;
    tty->term.c_lflag |= ECHO;
    tty->term.c_lflag |= ICANON;

    Tty_Clear(tty);

    return tty;
}

void destroyTty(Tty* tty) {
    FifoBuffer_destroy(tty->keyBuffer);
    kfree(tty->buffer);
    kfree(tty);
}

void Tty_Print(Tty* tty, int row, int column, const char* text) {
    unsigned char * video = tty->buffer;

    video += (row * tty->columnCount + column) * 2;
    while(*text != 0) {
        *video++ = *text++;
        *video++ = tty->color;
    }
}

//One line
void Tty_ScrollUp(Tty* tty) {
    unsigned char * videoLine = tty->buffer;
    unsigned char * videoLineNext = tty->buffer;
    int line = 0;
    int column = 0;

    for (line = 0; line < tty->lineCount - 1; ++line) {
        for (column = 0; column < tty->columnCount; ++column) {
            videoLine = tty->buffer + (line * tty->columnCount + column) * 2;
            videoLineNext = tty->buffer + ((line + 1) * tty->columnCount + column) * 2;

            videoLine[0] = videoLineNext[0];
            videoLine[1] = videoLineNext[1];
        }
    }

    //Last line should be empty.
    unsigned char * lastLine = tty->buffer + ((tty->lineCount - 1) * tty->columnCount) * 2;
    for (int i = 0; i < tty->columnCount * 2; i += 2) {
        lastLine[i] = 0;
        lastLine[i + 1] = tty->color;
    }
}

void Tty_Clear(Tty* tty) {
    unsigned char * video = tty->buffer;
    int i = 0;

    for (i = 0; i < tty->lineCount * tty->columnCount; ++i) {
        *video++ = 0;
        *video++ = tty->color;
    }

    tty->currentLine = 0;
    tty->currentColumn = 0;
}

void Tty_PutChar(Tty* tty, char c) {
    unsigned char * video = tty->buffer;

    if ('\n' == c || '\r' == c) {
        ++tty->currentLine;
        tty->currentColumn = 0;

        if (tty->currentLine >= tty->lineCount - 0) {
            --tty->currentLine;
            Tty_ScrollUp(tty);
        }

        Tty_MoveCursor(tty, tty->currentLine, tty->currentColumn);
        return;
    }
    else if ('\b' == c) {
        if (tty->currentColumn > 0) {
            --tty->currentColumn;
            c = '\0';
            video = tty->buffer + (tty->currentLine * tty->columnCount + tty->currentColumn) * 2;
            video[0] = c;
            video[1] = tty->color;
            Tty_MoveCursor(tty, tty->currentLine, tty->currentColumn);
            return;
        }
        else if (tty->currentColumn == 0) {
            if (tty->currentLine > 0) {
                --tty->currentLine;
                tty->currentColumn = tty->columnCount - 1;
                c = '\0';
                video = tty->buffer + (tty->currentLine * tty->columnCount + tty->currentColumn) * 2;
                video[0] = c;
                video[1] = tty->color;
                Tty_MoveCursor(tty, tty->currentLine, tty->currentColumn);
                return;
            }
        }
    }

    if (tty->currentColumn >= tty->columnCount) {
        ++tty->currentLine;
        tty->currentColumn = 0;
    }

    if (tty->currentLine >= tty->lineCount - 0) {
        --tty->currentLine;
        Tty_ScrollUp(tty);
    }

    video += (tty->currentLine * tty->columnCount + tty->currentColumn) * 2;

    video[0] = c;
    video[1] = tty->color;

    ++tty->currentColumn;

    Tty_MoveCursor(tty, tty->currentLine, tty->currentColumn);
}

void Tty_PutText(Tty* tty, const char* text) {
    const char* c = text;
    while (*c) {
        Tty_PutChar(tty, *c);
        ++c;
    }
}

void Tty_MoveCursor(Tty* tty, uint16 line, uint16 column) {
    tty->currentLine = line;
    tty->currentColumn = column;
}