Merge branch 'feature/#20-heredoc' of shimatta/shellmatta into develop
This commit is contained in:
commit
017c3c050e
1
.gitignore
vendored
1
.gitignore
vendored
@ -1 +1,2 @@
|
|||||||
output
|
output
|
||||||
|
output
|
||||||
|
@ -91,6 +91,7 @@ typedef struct
|
|||||||
char *buffer; /**< input buffer */
|
char *buffer; /**< input buffer */
|
||||||
uint32_t bufferSize; /**< size of the input buffer */
|
uint32_t bufferSize; /**< size of the input buffer */
|
||||||
uint32_t inputCount; /**< offset of the current write operation */
|
uint32_t inputCount; /**< offset of the current write operation */
|
||||||
|
uint32_t lastNewlineIdx; /**< index of the lest newline */
|
||||||
uint32_t cursor; /**< offset where the cursor is at */
|
uint32_t cursor; /**< offset where the cursor is at */
|
||||||
char *historyBuffer; /**< buffer to store the last commands */
|
char *historyBuffer; /**< buffer to store the last commands */
|
||||||
uint32_t historyBufferSize; /**< size of the history buffer */
|
uint32_t historyBufferSize; /**< size of the history buffer */
|
||||||
@ -100,7 +101,10 @@ typedef struct
|
|||||||
bool historyReadUp; /**< flag to show the last history dir */
|
bool historyReadUp; /**< flag to show the last history dir */
|
||||||
uint32_t tabCounter; /**< counts the tabulator key presses */
|
uint32_t tabCounter; /**< counts the tabulator key presses */
|
||||||
uint32_t escapeCounter; /**< counts the characters of an escape seq */
|
uint32_t escapeCounter; /**< counts the characters of an escape seq */
|
||||||
char escapeChars[4]; /**< buffer to save the escape characters */
|
char escapeChars[4u]; /**< buffer to save the escape characters */
|
||||||
|
uint32_t hereStartIdx; /**< heredoc start of "<<" */
|
||||||
|
uint32_t hereDelimiterIdx; /**< heredoc delimiter index in input */
|
||||||
|
uint32_t hereLength; /**< length of the heredoc delimiter */
|
||||||
bool echoEnabled; /**< if true the input is printed */
|
bool echoEnabled; /**< if true the input is printed */
|
||||||
bool dirty; /**< dirty flag to show changes */
|
bool dirty; /**< dirty flag to show changes */
|
||||||
const char *prompt; /**< prompt is printed after every command */
|
const char *prompt; /**< prompt is printed after every command */
|
||||||
|
121
example/main.c
Normal file
121
example/main.c
Normal file
@ -0,0 +1,121 @@
|
|||||||
|
/*
|
||||||
|
* main.c
|
||||||
|
*
|
||||||
|
* Created on: Jun 10, 2019
|
||||||
|
* Author: stefan
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include "shellmatta.h"
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <ncurses.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <termios.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <errno.h>
|
||||||
|
|
||||||
|
|
||||||
|
static bool exitRequest = false;
|
||||||
|
int f;
|
||||||
|
shellmatta_handle_t handle;
|
||||||
|
|
||||||
|
void set_blocking (int fd, int should_block)
|
||||||
|
{
|
||||||
|
struct termios tty;
|
||||||
|
memset (&tty, 0, sizeof tty);
|
||||||
|
if (tcgetattr (fd, &tty) != 0)
|
||||||
|
{
|
||||||
|
printf ("error %d from tggetattr", errno);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
tty.c_cc[VMIN] = should_block ? 1 : 0;
|
||||||
|
tty.c_cc[VTIME] = 5; // 0.5 seconds read timeout
|
||||||
|
|
||||||
|
if (tcsetattr (fd, TCSANOW, &tty) != 0)
|
||||||
|
printf ("error %d setting term attributes", errno);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static shellmatta_retCode_t doSomething(shellmatta_handle_t handle, const char *arguments, uint32_t length)
|
||||||
|
{
|
||||||
|
shellmatta_printf(handle, "%s - length: %u", arguments, length);
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
shellmatta_cmd_t doSomethingCmd = {"doSomething", "do", "Function does something", "use me, please", doSomething, NULL};
|
||||||
|
|
||||||
|
static shellmatta_retCode_t doSome(shellmatta_handle_t handle, const char *arguments, uint32_t length)
|
||||||
|
{
|
||||||
|
|
||||||
|
shellmatta_write(handle, "blubb\r\n", 7u);
|
||||||
|
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
shellmatta_cmd_t doSomeCmd = {"adoSome2", "adof2", "Function does something", "use me, please", doSome, NULL};
|
||||||
|
|
||||||
|
|
||||||
|
static shellmatta_retCode_t quit(shellmatta_handle_t handle, const char *arguments, uint32_t length)
|
||||||
|
{
|
||||||
|
exitRequest = true;
|
||||||
|
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
shellmatta_cmd_t quitCommand = {"quit", "q", "Function quits the shell", "", quit, NULL};
|
||||||
|
|
||||||
|
|
||||||
|
shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write(f, data, length);
|
||||||
|
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(void)
|
||||||
|
{
|
||||||
|
static char buffer[1024];
|
||||||
|
static char historyBuffer[4096];
|
||||||
|
static shellmatta_instance_t instance;
|
||||||
|
|
||||||
|
f = open("/dev/pts/3", O_RDWR | O_SYNC);
|
||||||
|
|
||||||
|
if (f < 0)
|
||||||
|
{
|
||||||
|
printf("failure %d\n", errno);
|
||||||
|
return f;
|
||||||
|
}
|
||||||
|
|
||||||
|
set_blocking (f, 1);
|
||||||
|
|
||||||
|
shellmatta_doInit( &instance,
|
||||||
|
&handle,
|
||||||
|
buffer,
|
||||||
|
sizeof(buffer),
|
||||||
|
historyBuffer,
|
||||||
|
sizeof(historyBuffer),
|
||||||
|
"shellmatta->",
|
||||||
|
NULL,
|
||||||
|
writeFct);
|
||||||
|
shellmatta_addCmd(handle, &doSomethingCmd);
|
||||||
|
shellmatta_addCmd(handle, &doSomeCmd);
|
||||||
|
shellmatta_addCmd(handle, &quitCommand);
|
||||||
|
|
||||||
|
while(exitRequest == false)
|
||||||
|
{
|
||||||
|
char c;
|
||||||
|
|
||||||
|
int res = 0;
|
||||||
|
res = read (f, &c, 1);
|
||||||
|
|
||||||
|
fprintf(stdout, "0x%02x \n", c);
|
||||||
|
fflush(stdout);
|
||||||
|
|
||||||
|
shellmatta_processData(handle, &c, res);
|
||||||
|
}
|
||||||
|
|
||||||
|
close(f);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
135
makefile
Normal file
135
makefile
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
#
|
||||||
|
# Copyright (c) 2019 Stefan Strobel <stefan.strobel@shimatta.net>
|
||||||
|
#
|
||||||
|
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||||
|
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
|
# file, You can obtain one at https://mozilla.org/MPL/2.0/.
|
||||||
|
#
|
||||||
|
|
||||||
|
OBJ_DIR := output/
|
||||||
|
|
||||||
|
CC := gcc
|
||||||
|
CPP := g++
|
||||||
|
LN := ln
|
||||||
|
|
||||||
|
SOURCES := src/shellmatta.c \
|
||||||
|
src/shellmatta_autocomplete.c \
|
||||||
|
src/shellmatta_history.c \
|
||||||
|
src/shellmatta_utils.c \
|
||||||
|
src/shellmatta_escape.c
|
||||||
|
|
||||||
|
INCLUDES := api .
|
||||||
|
|
||||||
|
UNITTEST_SOURCES := test/unittest/test_main.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_writeEcho.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_shellItoa.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_saveCursorPos.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_restoreCursorPos.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_eraseLine.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_rewindCursor.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_forwardCursor.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_clearInput.cpp \
|
||||||
|
test/unittest/shellmatta_utils/test_utils_insertChars.cpp
|
||||||
|
|
||||||
|
INTEGRATIONTEST_SOURCES := test/integrationtest/test_main.cpp \
|
||||||
|
test/integrationtest/test_integration.cpp
|
||||||
|
|
||||||
|
UNITTEST_CPPOBJ := $(patsubst %.cpp,$(OBJ_DIR)%.o,$(UNITTEST_SOURCES))
|
||||||
|
|
||||||
|
INTEGRATIONTEST_CPPOBJ := $(patsubst %.cpp,$(OBJ_DIR)%.o,$(INTEGRATIONTEST_SOURCES))
|
||||||
|
|
||||||
|
CFLAGS := $(INCLUDES:%=-I%) -g
|
||||||
|
TESTFLAGS := $(INCLUDES:%=-I%) -g -fprofile-arcs -ftest-coverage
|
||||||
|
TESTLFLAGS := -fprofile-arcs -Wl,--allow-multiple-definition
|
||||||
|
|
||||||
|
DEPEND = -MT $@ -MF "$(@:%.o=%.d)" -MG -MM
|
||||||
|
|
||||||
|
COBJ := $(patsubst %.c,$(OBJ_DIR)%.o,$(SOURCES))
|
||||||
|
|
||||||
|
EXAMPLE_SOURCES := example/main.c
|
||||||
|
EXAMPLE_COBJ := $(patsubst %.c,$(OBJ_DIR)%.o,$(EXAMPLE_SOURCES))
|
||||||
|
|
||||||
|
EXAMPLE_TARGET := $(OBJ_DIR)example/example
|
||||||
|
|
||||||
|
UNITTEST_TARGET := $(OBJ_DIR)test/unittest/unittest
|
||||||
|
|
||||||
|
INTEGRATIONTEST_TARGET := $(OBJ_DIR)test/integrationtest/integrationtest
|
||||||
|
|
||||||
|
OBJ := $(COBJ) $(EXAMPLE_COBJ) $(UNITTEST_CPPOBJ) $(INTEGRATIONTEST_CPPOBJ)
|
||||||
|
DEPS := $(OBJ:%.o=%.d)
|
||||||
|
|
||||||
|
export
|
||||||
|
|
||||||
|
help:
|
||||||
|
@echo Shellmatta help
|
||||||
|
@echo -------------------------
|
||||||
|
@echo test - run all tests
|
||||||
|
@echo example - build example
|
||||||
|
@echo -------------------------
|
||||||
|
|
||||||
|
test: unittest integrationtest
|
||||||
|
|
||||||
|
unittest: $(UNITTEST_TARGET)
|
||||||
|
- @mkdir -p output/test/unittest/report
|
||||||
|
@echo running test:
|
||||||
|
-$(UNITTEST_TARGET)
|
||||||
|
#gcov -o output/test $(TEST_CPPOBJ) -r
|
||||||
|
gcovr --html-details --output $(OBJ_DIR)test/unittest/report/report.html output/test/unittest -f src -f api
|
||||||
|
#-rm *.gcov
|
||||||
|
|
||||||
|
integrationtest: $(INTEGRATIONTEST_TARGET)
|
||||||
|
- @mkdir -p output/test/integrationtest/report
|
||||||
|
@echo running test:
|
||||||
|
-$(INTEGRATIONTEST_TARGET)
|
||||||
|
#gcov -o output/test $(TEST_CPPOBJ) -r
|
||||||
|
gcovr --html-details --output $(OBJ_DIR)test/integrationtest/report/report.html output/test/integrationtest -f src -f api
|
||||||
|
#-rm *.gcov
|
||||||
|
|
||||||
|
example: $(EXAMPLE_TARGET)
|
||||||
|
@echo building example
|
||||||
|
|
||||||
|
doc:
|
||||||
|
- @mkdir -p output/doc/html
|
||||||
|
- @mkdir -p output/doc/latex
|
||||||
|
doxygen settings/doxygen/doxyfile
|
||||||
|
|
||||||
|
clean:
|
||||||
|
- rm -rf $(OBJ_DIR)
|
||||||
|
|
||||||
|
$(EXAMPLE_TARGET): $(COBJ) $(EXAMPLE_COBJ)
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
$(CC) $(LFLAGS) $(LIB_PATH) -o $@ $^ $(LIBS)
|
||||||
|
|
||||||
|
$(UNITTEST_TARGET): $(UNITTEST_CPPOBJ)
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
$(CPP) $(TESTLFLAGS) $(LIB_PATH) -o $@ $^ $(LIBS)
|
||||||
|
|
||||||
|
$(INTEGRATIONTEST_TARGET): $(INTEGRATIONTEST_CPPOBJ) $(COBJ)
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
$(CPP) $(TESTLFLAGS) $(LIB_PATH) -o $@ $^ $(LIBS)
|
||||||
|
|
||||||
|
$(TARGET): $(OBJ)
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
$(CC) $(LFLAGS) $(LIB_PATH) -o $@ $^ $(LIBS)
|
||||||
|
|
||||||
|
$(COBJ):
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
@$(CC) -c $(CFLAGS) $(DEPEND) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.c))
|
||||||
|
$(CC) -c $(CFLAGS) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.c))
|
||||||
|
|
||||||
|
$(EXAMPLE_COBJ):
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
@$(CC) -c $(CFLAGS) $(DEPEND) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.c))
|
||||||
|
$(CC) -c $(CFLAGS) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.c))
|
||||||
|
|
||||||
|
$(UNITTEST_CPPOBJ) $(INTEGRATIONTEST_CPPOBJ):
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
@$(CPP) -c $(TESTFLAGS) $(DEPEND) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.cpp))
|
||||||
|
$(CPP) -c $(TESTFLAGS) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.cpp))
|
||||||
|
|
||||||
|
%.o: %.cpp
|
||||||
|
- @mkdir -p $(@D)
|
||||||
|
@$(CPP) -c $(CFLAGS) $(DEPEND) -o $@ $(subst $(OBJ_DIR), ,$(@:%.o=%.c))
|
||||||
|
$(CPP) -c $(CFLAGS) -o $@ $<
|
||||||
|
|
||||||
|
-include $(DEPS)
|
2536
settings/doxygen/doxyfile
Normal file
2536
settings/doxygen/doxyfile
Normal file
File diff suppressed because it is too large
Load Diff
129
src/shellmatta.c
129
src/shellmatta.c
@ -74,6 +74,7 @@ shellmatta_retCode_t shellmatta_doInit(
|
|||||||
inst->buffer = buffer;
|
inst->buffer = buffer;
|
||||||
inst->bufferSize = bufferSize;
|
inst->bufferSize = bufferSize;
|
||||||
inst->inputCount = 0u;
|
inst->inputCount = 0u;
|
||||||
|
inst->lastNewlineIdx = 0u;
|
||||||
inst->cursor = 0u;
|
inst->cursor = 0u;
|
||||||
inst->historyBuffer = historyBuffer;
|
inst->historyBuffer = historyBuffer;
|
||||||
inst->historyBufferSize = historyBufferSize;
|
inst->historyBufferSize = historyBufferSize;
|
||||||
@ -87,6 +88,9 @@ shellmatta_retCode_t shellmatta_doInit(
|
|||||||
inst->dirty = false;
|
inst->dirty = false;
|
||||||
inst->tabCounter = 0u;
|
inst->tabCounter = 0u;
|
||||||
inst->escapeCounter = 0u;
|
inst->escapeCounter = 0u;
|
||||||
|
inst->hereStartIdx = 0u;
|
||||||
|
inst->hereDelimiterIdx = 0u;
|
||||||
|
inst->hereLength = 0u;
|
||||||
inst->mode = SHELLMATTA_MODE_INSERT;
|
inst->mode = SHELLMATTA_MODE_INSERT;
|
||||||
inst->cmdList = &helpCmd;
|
inst->cmdList = &helpCmd;
|
||||||
inst->cmdListIsConst = false;
|
inst->cmdListIsConst = false;
|
||||||
@ -194,6 +198,12 @@ shellmatta_retCode_t shellmatta_processData(shellmatta_handle_t handle,
|
|||||||
shellmatta_cmd_t *cmd;
|
shellmatta_cmd_t *cmd;
|
||||||
uint8_t cmdExecuted = 0u;
|
uint8_t cmdExecuted = 0u;
|
||||||
uint32_t cmdLen;
|
uint32_t cmdLen;
|
||||||
|
char *tempString;
|
||||||
|
char *argumentString;
|
||||||
|
uint32_t argumentLength;
|
||||||
|
uint32_t byteCounter;
|
||||||
|
uint32_t idx;
|
||||||
|
|
||||||
shellmatta_retCode_t ret = SHELLMATTA_OK;
|
shellmatta_retCode_t ret = SHELLMATTA_OK;
|
||||||
shellmatta_instance_t *inst = (shellmatta_instance_t*)handle;
|
shellmatta_instance_t *inst = (shellmatta_instance_t*)handle;
|
||||||
|
|
||||||
@ -202,7 +212,7 @@ shellmatta_retCode_t shellmatta_processData(shellmatta_handle_t handle,
|
|||||||
&& (SHELLMATTA_MAGIC == inst->magic))
|
&& (SHELLMATTA_MAGIC == inst->magic))
|
||||||
{
|
{
|
||||||
/** -# process byte wise */
|
/** -# process byte wise */
|
||||||
for (uint32_t i = 0u; i < size; i++)
|
for (byteCounter = 0u; byteCounter < size; byteCounter++)
|
||||||
{
|
{
|
||||||
/** -# handle escape sequences */
|
/** -# handle escape sequences */
|
||||||
if(inst->escapeCounter != 0u)
|
if(inst->escapeCounter != 0u)
|
||||||
@ -218,19 +228,115 @@ shellmatta_retCode_t shellmatta_processData(shellmatta_handle_t handle,
|
|||||||
/** -# handle return as start of processing the command */
|
/** -# handle return as start of processing the command */
|
||||||
else if ('\r' == *data)
|
else if ('\r' == *data)
|
||||||
{
|
{
|
||||||
cmd = inst->cmdList;
|
if(0u == inst->hereLength)
|
||||||
inst->buffer[inst->inputCount] = 0u;
|
{
|
||||||
|
/**
|
||||||
|
* \dot
|
||||||
|
* digraph heredocParser {
|
||||||
|
* start -> wait [ label="<< in first line - store delimiter" ];
|
||||||
|
* wait -> wait [ label="delimiter not detected" ];
|
||||||
|
* wait -> end [ label="delimiter found - remove all heredoc stuff and send the input to the command" ];
|
||||||
|
* }
|
||||||
|
* \enddot */
|
||||||
|
|
||||||
|
/** -# check for heredoc */
|
||||||
|
tempString = strstr(inst->buffer, "<<");
|
||||||
|
if(NULL != tempString)
|
||||||
|
{
|
||||||
|
/*' -# check if length of heredoc delimiter is valid */
|
||||||
|
if(inst->inputCount > ((uint32_t)(tempString - inst->buffer) + 2u))
|
||||||
|
{
|
||||||
|
inst->hereStartIdx = (uint32_t)(tempString - inst->buffer);
|
||||||
|
inst->hereDelimiterIdx = inst->hereStartIdx + 2u;
|
||||||
|
while((inst->hereDelimiterIdx < inst->inputCount)
|
||||||
|
&& ( ('\0' == inst->buffer[inst->hereDelimiterIdx])
|
||||||
|
|| (' ' == inst->buffer[inst->hereDelimiterIdx])))
|
||||||
|
{
|
||||||
|
inst->hereDelimiterIdx ++;
|
||||||
|
}
|
||||||
|
|
||||||
|
inst->hereLength = inst->inputCount - inst->hereDelimiterIdx;
|
||||||
|
|
||||||
|
inst->dirty = true;
|
||||||
|
utils_insertChars(inst, data, 1);
|
||||||
|
inst->lastNewlineIdx = inst->inputCount;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
inst->hereLength = 0u;
|
||||||
|
|
||||||
|
/** -# store the current command and reset the history buffer */
|
||||||
|
inst->dirty = true;
|
||||||
|
history_storeCmd(inst);
|
||||||
|
history_reset(inst);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
argumentString = inst->buffer;
|
||||||
|
argumentLength = inst->inputCount;
|
||||||
|
|
||||||
|
/** -# store the current command and reset the history buffer */
|
||||||
|
inst->dirty = true;
|
||||||
|
history_storeCmd(inst);
|
||||||
|
history_reset(inst);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
tempString = &inst->buffer[inst->lastNewlineIdx];
|
||||||
|
cmdLen = inst->inputCount - inst->lastNewlineIdx;
|
||||||
|
|
||||||
|
/** -# skip newline characters before comparison */
|
||||||
|
while(('\n' == *tempString) || ('\r' == *tempString))
|
||||||
|
{
|
||||||
|
tempString ++;
|
||||||
|
cmdLen --;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( (inst->hereLength == cmdLen)
|
||||||
|
&& (0 == strncmp( &inst->buffer[inst->hereDelimiterIdx],
|
||||||
|
tempString,
|
||||||
|
inst->hereLength)))
|
||||||
|
{
|
||||||
|
argumentLength = inst->lastNewlineIdx;
|
||||||
|
|
||||||
/** -# store the current command and reset the history buffer */
|
/** -# store the current command and reset the history buffer */
|
||||||
inst->dirty = true;
|
inst->dirty = true;
|
||||||
history_storeCmd(inst);
|
history_storeCmd(inst);
|
||||||
history_reset(inst);
|
history_reset(inst);
|
||||||
|
|
||||||
|
|
||||||
|
/* TODO it is difficult to store the complete command in the history buffer if it is restructured before...
|
||||||
|
* So this should be an extra function that can be called after parsing the command and before calling the command funktion */
|
||||||
|
for(idx = 1u; idx <= inst->hereStartIdx; idx++)
|
||||||
|
{
|
||||||
|
inst->buffer[inst->hereDelimiterIdx + inst->hereLength - idx] = inst->buffer[inst->hereStartIdx - idx];
|
||||||
|
}
|
||||||
|
|
||||||
|
argumentString = &(inst->buffer[inst->hereDelimiterIdx + inst->hereLength - inst->hereStartIdx]);
|
||||||
|
argumentLength = inst->lastNewlineIdx - ((inst->hereDelimiterIdx + inst->hereLength) - inst->hereStartIdx);
|
||||||
|
inst->hereLength = 0u;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
inst->lastNewlineIdx = inst->inputCount;
|
||||||
|
utils_insertChars(inst, data, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(0u == inst->hereLength)
|
||||||
|
{
|
||||||
|
cmd = inst->cmdList;
|
||||||
|
argumentString[argumentLength] = 0u;
|
||||||
|
|
||||||
/** -# determine the cmd len (chars until first space or \0 is found */
|
/** -# determine the cmd len (chars until first space or \0 is found */
|
||||||
cmdLen = 0u;
|
cmdLen = 0u;
|
||||||
while( (cmdLen < inst->inputCount)
|
while( (cmdLen < argumentLength)
|
||||||
&& (' ' != inst->buffer[cmdLen])
|
&& (' ' != argumentString[cmdLen])
|
||||||
&& ('\0' != inst->buffer[cmdLen]))
|
&& ('\r' != argumentString[cmdLen])
|
||||||
|
&& ('\n' != argumentString[cmdLen])
|
||||||
|
&& ('\0' != argumentString[cmdLen]))
|
||||||
{
|
{
|
||||||
cmdLen ++;
|
cmdLen ++;
|
||||||
}
|
}
|
||||||
@ -239,11 +345,11 @@ shellmatta_retCode_t shellmatta_processData(shellmatta_handle_t handle,
|
|||||||
while (NULL != cmd)
|
while (NULL != cmd)
|
||||||
{
|
{
|
||||||
/** -# compare command string and length */
|
/** -# compare command string and length */
|
||||||
if ( ((0 == strncmp( inst->buffer,
|
if ( ((0 == strncmp( argumentString,
|
||||||
cmd->cmd,
|
cmd->cmd,
|
||||||
cmdLen))
|
cmdLen))
|
||||||
&& (cmdLen == strlen(cmd->cmd)))
|
&& (cmdLen == strlen(cmd->cmd)))
|
||||||
|| ((0 == strncmp( inst->buffer,
|
|| ((0 == strncmp( argumentString,
|
||||||
cmd->cmdAlias,
|
cmd->cmdAlias,
|
||||||
cmdLen))
|
cmdLen))
|
||||||
&& (cmdLen == strlen(cmd->cmdAlias))))
|
&& (cmdLen == strlen(cmd->cmdAlias))))
|
||||||
@ -251,7 +357,7 @@ shellmatta_retCode_t shellmatta_processData(shellmatta_handle_t handle,
|
|||||||
inst->write("\r\n", 2u);
|
inst->write("\r\n", 2u);
|
||||||
|
|
||||||
cmdExecuted = 1u;
|
cmdExecuted = 1u;
|
||||||
cmd->cmdFct(inst, inst->buffer, inst->inputCount);
|
cmd->cmdFct(inst, argumentString, argumentLength);
|
||||||
cmd = NULL;
|
cmd = NULL;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -262,13 +368,14 @@ shellmatta_retCode_t shellmatta_processData(shellmatta_handle_t handle,
|
|||||||
|
|
||||||
if ((cmdExecuted == 0u) && (inst->inputCount > 0))
|
if ((cmdExecuted == 0u) && (inst->inputCount > 0))
|
||||||
{
|
{
|
||||||
inst->buffer[inst->inputCount] = '\0';
|
|
||||||
inst->write("\r\nCommand: ", 11u);
|
inst->write("\r\nCommand: ", 11u);
|
||||||
inst->write(inst->buffer, inst->inputCount);
|
inst->write(argumentString, argumentLength);
|
||||||
inst->write(" not found", 10u);
|
inst->write(" not found", 10u);
|
||||||
}
|
}
|
||||||
utils_terminateInput(inst);
|
utils_terminateInput(inst);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
/** -# check for tabulator key - auto complete */
|
/** -# check for tabulator key - auto complete */
|
||||||
else if('\t' == *data)
|
else if('\t' == *data)
|
||||||
{
|
{
|
||||||
|
@ -336,6 +336,8 @@ shellmatta_cmd_t helpCmd = {"help", "h", "Print this help text", "help", helpCmd
|
|||||||
void utils_terminateInput(shellmatta_instance_t *inst)
|
void utils_terminateInput(shellmatta_instance_t *inst)
|
||||||
{
|
{
|
||||||
inst->inputCount = 0u;
|
inst->inputCount = 0u;
|
||||||
|
inst->lastNewlineIdx = 0u;
|
||||||
|
inst->hereLength = 0u;
|
||||||
inst->cursor = 0u;
|
inst->cursor = 0u;
|
||||||
inst->write("\r\n", 2u);
|
inst->write("\r\n", 2u);
|
||||||
inst->write(inst->prompt, strlen(inst->prompt));
|
inst->write(inst->prompt, strlen(inst->prompt));
|
||||||
|
16865
test/framework/catch.hpp
Normal file
16865
test/framework/catch.hpp
Normal file
File diff suppressed because it is too large
Load Diff
122
test/integrationtest/test_integration.cpp
Normal file
122
test/integrationtest/test_integration.cpp
Normal file
@ -0,0 +1,122 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
extern "C" {
|
||||||
|
#include "shellmatta.h"
|
||||||
|
}
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static char write_data[1024];
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
while((length > 0) && (write_length < sizeof(write_data)))
|
||||||
|
{
|
||||||
|
write_data[write_length] = *data;
|
||||||
|
data ++;
|
||||||
|
length --;
|
||||||
|
write_length ++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
static shellmatta_retCode_t doSomething(shellmatta_handle_t handle, const char *arguments, uint32_t length)
|
||||||
|
{
|
||||||
|
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
shellmatta_cmd_t doSomethingCmd = {"doSomething", "do", "Function does something", "use me, please", doSomething, NULL};
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta empty function" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
shellmatta_handle_t handle;
|
||||||
|
char buffer[1024];
|
||||||
|
char historyBuffer[1024];
|
||||||
|
char *dummyData = "\r\nshellmatta->";
|
||||||
|
|
||||||
|
shellmatta_doInit( &inst,
|
||||||
|
&handle,
|
||||||
|
buffer,
|
||||||
|
sizeof(buffer),
|
||||||
|
historyBuffer,
|
||||||
|
sizeof(historyBuffer),
|
||||||
|
"shellmatta->",
|
||||||
|
NULL,
|
||||||
|
writeFct);
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
shellmatta_processData(handle, "\r", 1);
|
||||||
|
|
||||||
|
CHECK( write_length == 14u);
|
||||||
|
REQUIRE( strcmp(dummyData, write_data) == 0);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta help function" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
shellmatta_handle_t handle;
|
||||||
|
char buffer[1024];
|
||||||
|
char historyBuffer[1024];
|
||||||
|
char *dummyData = "h\r\n"
|
||||||
|
"doSomething do Function does something use me, please\r\n"
|
||||||
|
"help h Print this help text help\r\n"
|
||||||
|
"\r\nshellmatta->";
|
||||||
|
|
||||||
|
shellmatta_doInit( &inst,
|
||||||
|
&handle,
|
||||||
|
buffer,
|
||||||
|
sizeof(buffer),
|
||||||
|
historyBuffer,
|
||||||
|
sizeof(historyBuffer),
|
||||||
|
"shellmatta->",
|
||||||
|
NULL,
|
||||||
|
writeFct);
|
||||||
|
shellmatta_addCmd(handle, &doSomethingCmd);
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
shellmatta_processData(handle, "h\r", 2);
|
||||||
|
|
||||||
|
CHECK( write_length == 123u);
|
||||||
|
CHECK( strcmp(dummyData, write_data) == 0);
|
||||||
|
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
dummyData = "h 564 321 56 465 46\r\n"
|
||||||
|
"doSomething do Function does something use me, please\r\n"
|
||||||
|
"help h Print this help text help\r\n"
|
||||||
|
"\r\nshellmatta->";
|
||||||
|
|
||||||
|
shellmatta_processData(handle, "h 564 321 56 465 46\r", 20);
|
||||||
|
|
||||||
|
CHECK( write_length == 141u);
|
||||||
|
CHECK( strcmp(dummyData, write_data) == 0);
|
||||||
|
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
dummyData = "hr\r\n"
|
||||||
|
"Command: hr not found"
|
||||||
|
"\r\nshellmatta->";
|
||||||
|
|
||||||
|
shellmatta_processData(handle, "hr\r", 3);
|
||||||
|
|
||||||
|
CHECK( write_length == 39u);
|
||||||
|
REQUIRE( strcmp(dummyData, write_data) == 0);
|
||||||
|
}
|
||||||
|
|
7
test/integrationtest/test_main.cpp
Normal file
7
test/integrationtest/test_main.cpp
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
// 010-TestCase.cpp
|
||||||
|
|
||||||
|
// Let Catch provide main():
|
||||||
|
#define CATCH_CONFIG_MAIN
|
||||||
|
|
||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
|
26
test/unittest/shellmatta_utils/test_utils_clearInput.cpp
Normal file
26
test/unittest/shellmatta_utils/test_utils_clearInput.cpp
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_clearInput normal call" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
utils_clearInput(&inst);
|
||||||
|
|
||||||
|
CHECK( inst.cursor == 0);
|
||||||
|
REQUIRE( inst.inputCount == 0);
|
||||||
|
}
|
41
test/unittest/shellmatta_utils/test_utils_eraseLine.cpp
Normal file
41
test/unittest/shellmatta_utils/test_utils_eraseLine.cpp
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static char write_data[10];
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
strncpy(write_data, data, length);
|
||||||
|
write_length = length;
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_eraseLine" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_eraseLine(&inst);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 3u);
|
||||||
|
REQUIRE( strncmp("\e[K", write_data, 3u) == 0);
|
||||||
|
}
|
117
test/unittest/shellmatta_utils/test_utils_forwardCursor.cpp
Normal file
117
test/unittest/shellmatta_utils/test_utils_forwardCursor.cpp
Normal file
@ -0,0 +1,117 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static char write_data[10];
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
strncpy(write_data, data, length);
|
||||||
|
write_length = length;
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_forwardCursor normal" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 20;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_forwardCursor(&inst, 5u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 4u);
|
||||||
|
REQUIRE( strncmp("\e[5C", write_data, 4u) == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_forwardCursor normal echo off" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 20;
|
||||||
|
inst.echoEnabled = false;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_forwardCursor(&inst, 5u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 0u);
|
||||||
|
CHECK( write_length == 0u);
|
||||||
|
REQUIRE( strncmp("\0\0\0\0", write_data, 4u) == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_forwardCursor forward by 12 with cursor at 5 and input count at 10" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 5;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_forwardCursor(&inst, 12u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 4u);
|
||||||
|
REQUIRE( strncmp("\e[5C", write_data, 4u) == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_forwardCursor forward by 0" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_forwardCursor(&inst, 0u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 0u);
|
||||||
|
CHECK( write_length == 0u);
|
||||||
|
REQUIRE( strncmp("\0\0\0\0\0", write_data, 4u) == 0);
|
||||||
|
}
|
27
test/unittest/shellmatta_utils/test_utils_insertChars.cpp
Normal file
27
test/unittest/shellmatta_utils/test_utils_insertChars.cpp
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_insertChars normal call" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 8;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
utils_insertChars(&inst, "blksdflsd kfjlk", 4);
|
||||||
|
|
||||||
|
CHECK( inst.cursor == 12);
|
||||||
|
REQUIRE( inst.inputCount == 14);
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,41 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static char write_data[10];
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
strncpy(write_data, data, length);
|
||||||
|
write_length = length;
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_restoreCursorPos" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_restoreCursorPos(&inst);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 3u);
|
||||||
|
REQUIRE( strncmp("\e[u", write_data, 3u) == 0);
|
||||||
|
}
|
92
test/unittest/shellmatta_utils/test_utils_rewindCursor.cpp
Normal file
92
test/unittest/shellmatta_utils/test_utils_rewindCursor.cpp
Normal file
@ -0,0 +1,92 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static char write_data[10];
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
strncpy(write_data, data, length);
|
||||||
|
write_length = length;
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_rewindCursor normal" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_rewindCursor(&inst, 5u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 4u);
|
||||||
|
REQUIRE( strncmp("\e[5D", write_data, 4u) == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_rewindCursor rewind by 12 with cursor at 10" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_rewindCursor(&inst, 12u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 5u);
|
||||||
|
REQUIRE( strncmp("\e[10D", write_data, 5u) == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_rewindCursor rewind by 0" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_rewindCursor(&inst, 0u);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 0u);
|
||||||
|
CHECK( write_length == 0u);
|
||||||
|
REQUIRE( strncmp("\0\0\0\0\0", write_data, 4u) == 0);
|
||||||
|
}
|
41
test/unittest/shellmatta_utils/test_utils_saveCursorPos.cpp
Normal file
41
test/unittest/shellmatta_utils/test_utils_saveCursorPos.cpp
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static char write_data[10];
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
strncpy(write_data, data, length);
|
||||||
|
write_length = length;
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils_saveCursorPos" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
memset(write_data, 0, sizeof(write_data));
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_saveCursorPos(&inst);
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u);
|
||||||
|
CHECK( write_length == 3u);
|
||||||
|
REQUIRE( strncmp("\e[s", write_data, 3u) == 0);
|
||||||
|
}
|
52
test/unittest/shellmatta_utils/test_utils_shellItoa.cpp
Normal file
52
test/unittest/shellmatta_utils/test_utils_shellItoa.cpp
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - 123456 base 10" ) {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(123456, buffer, 10) == 6 );
|
||||||
|
REQUIRE( strcmp(buffer, "123456") == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - 0x0ABBCCDD base 16") {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(0x0ABBCCDD, buffer, 16) == 7 );
|
||||||
|
REQUIRE( strcmp(buffer, "ABBCCDD") == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - -574236 base 10") {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(-574236, buffer, 10) == 7 );
|
||||||
|
REQUIRE( strcmp(buffer, "-574236") == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - 0x80000000 base 2") {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(0x80000000, buffer, 2) == 33 );
|
||||||
|
REQUIRE( strcmp(buffer, "-10000000000000000000000000000000") == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - 0x7FFFFFFF base 2") {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(0x7FFFFFFF, buffer, 2) == 31 );
|
||||||
|
REQUIRE( strcmp(buffer, "1111111111111111111111111111111") == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - 0x7FFFFFFF base 1 - wrong base") {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(0x7FFFFFFF, buffer, 1) == 0 );
|
||||||
|
REQUIRE( strcmp(buffer, "\0") == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_utils.c - itoa - 0x7FFFFFFF base 17 - wrong base") {
|
||||||
|
char buffer[64];
|
||||||
|
memset(buffer, 0, sizeof(buffer));
|
||||||
|
CHECK( utils_shellItoa(0x7FFFFFFF, buffer, 17) == 0 );
|
||||||
|
REQUIRE( strcmp(buffer, "\0") == 0);
|
||||||
|
}
|
65
test/unittest/shellmatta_utils/test_utils_writeEcho.cpp
Normal file
65
test/unittest/shellmatta_utils/test_utils_writeEcho.cpp
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
#include "src/shellmatta_utils.c"
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
static uint32_t write_callCnt = 0u;
|
||||||
|
static const char *write_data;
|
||||||
|
static uint32_t write_length;
|
||||||
|
|
||||||
|
static shellmatta_retCode_t writeFct(const char* data, uint32_t length)
|
||||||
|
{
|
||||||
|
write_callCnt ++;
|
||||||
|
write_data = data;
|
||||||
|
write_length = length;
|
||||||
|
return SHELLMATTA_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_writeEcho echo enabled" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = true;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
write_data = 0u;
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_writeEcho(&inst, (char*)&dummyData, sizeof(dummyData));
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 1u );
|
||||||
|
CHECK( write_data == (char*)&dummyData );
|
||||||
|
REQUIRE( write_length == sizeof(dummyData));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE( "shellmatta_writeEcho echo disabled" ) {
|
||||||
|
|
||||||
|
shellmatta_instance_t inst;
|
||||||
|
char buffer[20];
|
||||||
|
char dummyData[29];
|
||||||
|
|
||||||
|
inst.buffer = buffer;
|
||||||
|
inst.bufferSize = 20;
|
||||||
|
inst.cursor = 10;
|
||||||
|
inst.inputCount = 10;
|
||||||
|
inst.echoEnabled = false;
|
||||||
|
|
||||||
|
inst.write = writeFct;
|
||||||
|
|
||||||
|
write_callCnt = 0u;
|
||||||
|
write_data = 0u;
|
||||||
|
write_length = 0u;
|
||||||
|
|
||||||
|
utils_writeEcho(&inst, (char*)&dummyData, sizeof(dummyData));
|
||||||
|
|
||||||
|
CHECK( write_callCnt == 0u );
|
||||||
|
CHECK( write_data == (char*)0u );
|
||||||
|
REQUIRE( write_length == 0u );
|
||||||
|
}
|
7
test/unittest/test_main.cpp
Normal file
7
test/unittest/test_main.cpp
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
// 010-TestCase.cpp
|
||||||
|
|
||||||
|
// Let Catch provide main():
|
||||||
|
#define CATCH_CONFIG_MAIN
|
||||||
|
|
||||||
|
#include "test/framework/catch.hpp"
|
||||||
|
|
Loading…
Reference in New Issue
Block a user