Home > front end >  error:hex escape sequence is out of range and write function is reading 12 bytes from a region of 3
error:hex escape sequence is out of range and write function is reading 12 bytes from a region of 3

Time:07-07

My code which is causing problems:

if (write(STDOUT_FILENO, "\x1b999C\x1b999B", 12) != 12)
        return -1;

Here, write() comes from <unistd.h>.

So, on compiling it providing two warnings. That hex escape sequence, "\x1b999C\x1b999B" is out of range and ‘write’ reading 12 bytes from a region of size 3.

What I am basically trying to do is move the cursor to the bottom right corner of the terminal window. Why are those warnings there ?

CodePudding user response:

Octal escapes use one to three (octal) digits only — "\033999C" is 5 characters plus a null byte.

Hex escapes use as many hex digits as follow the \x sequence. Therefore, "\x1b999C" contains a single hex character constant.

See §6.4.4.4 Character constants in the C11 standard for the specification.

There are at least two possible fixes. One is to encode \x1B as \033 (or \33 — they're the same, though if the text after the \x1B was 777A instead of 999C, then the triple-digit octal escape would be necessary.

if (write(STDOUT_FILENO, "\033999C\033999B", 10) != 10)

A second is to split the string and use string concatenation:

if (write(STDOUT_FILENO, "\x1B" "999C" "\x1B" "999B", 10) != 10)

This works because of what is specified in §5.1.1.2 Translation phases — where phase 5 converts escape sequences and phase 6 combines adjacent string literals.

I observe that there are 10 non-null characters in this — if you intended to write the byte 0x01 followed by 5 characters (twice), then 12 makes more sense, and you need to alter where the strings break, of course.

This test code prints 11:

#include <stdio.h>

int main(void)
{
    char data[] = "\x1b" "999C" "\x1b" "999B";
    printf("%zu\n", sizeof(data));
    return 0;
}

Remove the " " sequences, and GCC complains:

xe43.c: In function ‘main’:
xe43.c:5:19: error: hex escape sequence out of range [-Werror]
     char data[] = "\x1b999C\x1b999B";
                   ^~~~~~~~~~~~~~~~~~
xe43.c:5:19: error: hex escape sequence out of range [-Werror]
cc1: all warnings being treated as errors

I compile with the -Werror option; otherwise, it would only be a warning. If compiled without -Werror and run, it produces the answer 3, not 11.

  • Related