Example #1
0
static VOID FASTCALL
TuiCopyRect(PCHAR Dest, PTEXTMODE_SCREEN_BUFFER Buff, SMALL_RECT* Region)
{
    UINT SrcDelta, DestDelta;
    LONG i;
    PCHAR_INFO Src, SrcEnd;

    Src = ConioCoordToPointer(Buff, Region->Left, Region->Top);
    SrcDelta = Buff->ScreenBufferSize.X * sizeof(CHAR_INFO);
    SrcEnd = Buff->Buffer + Buff->ScreenBufferSize.Y * Buff->ScreenBufferSize.X * sizeof(CHAR_INFO);
    DestDelta = ConioRectWidth(Region) * 2 /* 2 == sizeof(CHAR) + sizeof(BYTE) */;
    for (i = Region->Top; i <= Region->Bottom; i++)
    {
        ConsoleUnicodeCharToAnsiChar(Buff->Header.Console, (PCHAR)Dest, &Src->Char.UnicodeChar);
        *(PBYTE)(Dest + 1) = (BYTE)Src->Attributes;

        Src += SrcDelta;
        if (SrcEnd <= Src)
        {
            Src -= Buff->ScreenBufferSize.Y * Buff->ScreenBufferSize.X * sizeof(CHAR_INFO);
        }
        Dest += DestDelta;
    }
}
Example #2
0
File: text.c Project: GYGit/reactos
NTSTATUS NTAPI
ConDrvReadConsoleOutputString(IN PCONSOLE Console,
                              IN PTEXTMODE_SCREEN_BUFFER Buffer,
                              IN CODE_TYPE CodeType,
                              OUT PVOID StringBuffer,
                              IN ULONG NumCodesToRead,
                              IN PCOORD ReadCoord,
                              OUT PCOORD EndCoord,
                              OUT PULONG CodesRead)
{
    SHORT Xpos, Ypos;
    PVOID ReadBuffer;
    ULONG i;
    ULONG CodeSize;
    PCHAR_INFO Ptr;

    if (Console == NULL || Buffer == NULL ||
        ReadCoord == NULL || EndCoord == NULL || CodesRead == NULL)
    {
        return STATUS_INVALID_PARAMETER;
    }

    /* Validity checks */
    ASSERT(Console == Buffer->Header.Console);
    ASSERT( (StringBuffer != NULL && NumCodesToRead >= 0) ||
            (StringBuffer == NULL && NumCodesToRead == 0) );

    switch (CodeType)
    {
        case CODE_ASCII:
            CodeSize = sizeof(CHAR);
            break;

        case CODE_UNICODE:
            CodeSize = sizeof(WCHAR);
            break;

        case CODE_ATTRIBUTE:
            CodeSize = sizeof(WORD);
            break;

        default:
            return STATUS_INVALID_PARAMETER;
    }

    ReadBuffer = StringBuffer;
    Xpos = ReadCoord->X;
    Ypos = (ReadCoord->Y + Buffer->VirtualY) % Buffer->ScreenBufferSize.Y;

    /*
     * MSDN (ReadConsoleOutputAttribute and ReadConsoleOutputCharacter) :
     *
     * If the number of attributes (resp. characters) to be read from extends
     * beyond the end of the specified screen buffer row, attributes (resp.
     * characters) are read from the next row. If the number of attributes
     * (resp. characters) to be read from extends beyond the end of the console
     * screen buffer, attributes (resp. characters) up to the end of the console
     * screen buffer are read.
     *
     * TODO: Do NOT loop up to NumCodesToRead, but stop before
     * if we are going to overflow...
     */
    // Ptr = ConioCoordToPointer(Buffer, Xpos, Ypos); // Doesn't work
    for (i = 0; i < min(NumCodesToRead, Buffer->ScreenBufferSize.X * Buffer->ScreenBufferSize.Y); ++i)
    {
        // Ptr = ConioCoordToPointer(Buffer, Xpos, Ypos); // Doesn't work either
        Ptr = &Buffer->Buffer[Xpos + Ypos * Buffer->ScreenBufferSize.X];

        switch (CodeType)
        {
            case CODE_ASCII:
                ConsoleUnicodeCharToAnsiChar(Console, (PCHAR)ReadBuffer, &Ptr->Char.UnicodeChar);
                break;

            case CODE_UNICODE:
                *(PWCHAR)ReadBuffer = Ptr->Char.UnicodeChar;
                break;

            case CODE_ATTRIBUTE:
                *(PWORD)ReadBuffer = Ptr->Attributes;
                break;
        }
        ReadBuffer = (PVOID)((ULONG_PTR)ReadBuffer + CodeSize);
        // ++Ptr;

        Xpos++;

        if (Xpos == Buffer->ScreenBufferSize.X)
        {
            Xpos = 0;
            Ypos++;

            if (Ypos == Buffer->ScreenBufferSize.Y)
            {
                Ypos = 0;
            }
        }
    }

    // switch (CodeType)
    // {
        // case CODE_UNICODE:
            // *(PWCHAR)ReadBuffer = 0;
            // break;

        // case CODE_ASCII:
            // *(PCHAR)ReadBuffer = 0;
            // break;

        // case CODE_ATTRIBUTE:
            // *(PWORD)ReadBuffer = 0;
            // break;
    // }

    EndCoord->X = Xpos;
    EndCoord->Y = (Ypos - Buffer->VirtualY + Buffer->ScreenBufferSize.Y) % Buffer->ScreenBufferSize.Y;

    *CodesRead = (ULONG)((ULONG_PTR)ReadBuffer - (ULONG_PTR)StringBuffer) / CodeSize;
    // <= NumCodesToRead

    return STATUS_SUCCESS;
}