'Why can I not combine these two chars using strcat when they are both chars?

I am working on a game for the 3ds and I want it to be a cmd type game (I just felt like it). I am trying to have this char move to whatever x and y int number I have but I am getting a error. This is my code.

/*
    Hello World example made by Aurelio Mannara for libctru
    This code was modified for the last time on: 12/12/2014 21:00 UTC+1
*/

#include <3ds.h>
#include <stdio.h>
#include <string.h>
int main(int argc, char **argv)
{
    gfxInitDefault();

    char player[1024] = "\x1b[";
    int tesx = 1;
    char tesxx = tesx + '0';
    char ot[] = ";";
    char oty[] = "H0";
    int test = 3;
    char testt = test + '0';
    //Initialize console on top screen. Using NULL as the second argument tells the console library to use the internal console structure as current one
    consoleInit(GFX_TOP, NULL);
    strcat(player, tesxx);
    strcat(player, ot);
    strcat(player, testt);
    strcat(player, oty);
    //Move the cursor to row 15 and column 19 and then prints "Hello World!"
    //To move the cursor you have to print "\x1b[r;cH", where r and c are respectively
    //the row and column where you want your cursor to move
    //The top screen has 30 rows and 50 columns
    //The bottom screen has 30 rows and 40 columns
    printf(player);

    // Main loop
    while (aptMainLoop())
    {
        //Scan all the inputs. This should be done once for each frame
        hidScanInput();

        //hidKeysDown returns information about which buttons have been just pressed (and they weren't in the previous frame)
        u32 kDown = hidKeysDown();

        if (kDown & KEY_START) break; // break in order to return to hbmenu

        // Flush and swap framebuffers
        gfxFlushBuffers();
        gfxSwapBuffers();

        //Wait for VBlank
        gspWaitForVBlank();
    }

    gfxExit();
    return 0;
}

This is my error. I am very new to C so i'm sorry if this is an easy bug. I tried searching but I couldn't find anything online.

C:/Users/Jeremy/Desktop/gaame/source/main.c:24:9: warning: 'strcat' offset 0 is out of the bounds [0, 0] [-Warray-bounds]
   24 |         strcat(player, testt);
      |         ^~~~~~~~~~~~~~~~~~~~~
C:/Users/Jeremy/Desktop/gaame/source/main.c:22:9: warning: '__builtin_stpcpy' offset 0 is out of the bounds [0, 0] [-Warray-bounds]
   22 |         strcat(player, tesxx);
      |         ^~~~~~~~~~~~~~~~~~~~~
c


Solution 1:[1]

The function strcat requires both of its arguments to be a pointer to a valid string, which is, by definition, a sequence of characters terminated by a null character.

However, in the line

strcat(player, tesxx);

the second function argument tesxx is not a pointer to a valid string. It is instead a simple char.

Therefore, I suggest that you change this line to the following:

player[2] = tesxx;
player[3] = '\0';

If the length of the string prior to this line is not guaranteed to be 2, then you could write this instead:

size_t len = strlen( player );
player[len+0] = tesxx;
player[len+1] = '\0';

Or, as suggested in one of the other answers, you can use strncat instead, which allows you to append single characters to the string:

strncat( player, &tesxx, 1 );

Alternatively, you could change the lines

strcat(player, tesxx);
strcat(player, ot);
strcat(player, testt);
strcat(player, oty);

to the following:

snprintf( player + 2, (sizeof player) - 2, "%c%s%c%s", tesxx, ot, testt, oty );

See the function snprintf for further information.

If the length of the string prior to these lines is not guaranteed to be 2, then you could write this instead:

size_t len = strlen( player );
snprintf( player + len, (sizeof player) - len, "%c%s%c%s", tesxx, ot, testt, oty );

You can also build the entire string player using the function snprintf:

    char player[1024];
    int tesx = 1;
    char tesxx = tesx + '0';
    char ot[] = ";";
    char oty[] = "H0";
    int test = 3;
    char testt = test + '0';
snprintf( player, sizeof player, "\x1b[%c%s%c%s", tesxx, ot, testt, oty );

Solution 2:[2]

strcat takes 2 string pointers:

char *strcat(char *dest, const char *src);

In strcat(player, tesxx) and strcat(player, testt) you pass a char instead of a char *, invoking undefined behavior. In order to append a single char to a C string in an array with extra space, you can write explicit code:

#include <string.h>

void append_char(char *dest, char c) {
    size_t len = strlen(dest);
    dest[len++] = c;
    dest[len] = '\0';
}

Or you can use strncat defined in <string.h> as:

char *strncat(char *dest, const char *src, size_t n);

This function appends at most n chars from src at the end of dest. You can pass the address of a char and a length of 1:

#include <string.h>

void append_char(char *dest, char c) {
    strncat(dest, &c, 1);
}

Yet for your code, it seems much simpler to use snprintf:

    char player[1024];  // probably too large
    int tesx = 1;
    int test = 3;
    consoleInit(GFX_TOP, NULL);
    // draw a `0` at screen coordinates tesx,test
    snprintf(player, sizeof player, "\x1b[%d;%dH0", tesx, test);

Solution 3:[3]

Consider the signature of strcat.

char *strcat( char *dest, const char *src );

It does not take a char * and a char, but rather two char *, and will expect two null-terminated strings.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2
Solution 3 Chris