first
This commit is contained in:
4
.gitignore
vendored
Normal file
4
.gitignore
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
build
|
||||
.cache
|
||||
bin
|
||||
|
||||
13
CMakeLists.txt
Normal file
13
CMakeLists.txt
Normal file
@@ -0,0 +1,13 @@
|
||||
cmake_minimum_required(VERSION 3.30.0)
|
||||
|
||||
project(sshGameServer VERSION 0.1)
|
||||
|
||||
set(CMAKE_CXX_STANDARD 20)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
|
||||
set(CMAKE_COLOR_MAKEFILE ON)
|
||||
set(CMAKE_COLOR_DIAGNOSTICS ON)
|
||||
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||
|
||||
add_subdirectory(source)
|
||||
add_subdirectory(external)
|
||||
3
external/CMakeLists.txt
vendored
Normal file
3
external/CMakeLists.txt
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
# ADD Externals HERE
|
||||
# add_subdirectory(external)
|
||||
|
||||
12
source/CMakeLists.txt
Normal file
12
source/CMakeLists.txt
Normal file
@@ -0,0 +1,12 @@
|
||||
# ADD SOURCES HERE
|
||||
set(SOURCE_FILES
|
||||
main.c
|
||||
)
|
||||
|
||||
add_executable(${PROJECT_NAME} ${SOURCE_FILES})
|
||||
|
||||
target_link_libraries(
|
||||
${PROJECT_NAME}
|
||||
ssh
|
||||
tart
|
||||
)
|
||||
403
source/main.c
Normal file
403
source/main.c
Normal file
@@ -0,0 +1,403 @@
|
||||
/* #############################################################################
|
||||
* # sshGameServer
|
||||
* This is a test
|
||||
*
|
||||
* AUTHER: PreacherDHM
|
||||
* DATE: 07/03/26
|
||||
* #############################################################################
|
||||
*/
|
||||
/* This is a sample implementation of a libssh based SSH server */
|
||||
/*
|
||||
Copyright 2003-2009 Aris Adamantiadis
|
||||
|
||||
This file is part of the SSH Library
|
||||
|
||||
You are free to copy this file, modify it in any way, consider it being public
|
||||
domain. This does not apply to the rest of the library though, but it is
|
||||
allowed to cut-and-paste working code from this file to any license of
|
||||
program.
|
||||
The goal is to show the API in action. It's not a reference on how terminal
|
||||
clients must be made or how a client should react.
|
||||
*/
|
||||
|
||||
|
||||
#include <libssh/libssh.h>
|
||||
#include <libssh/server.h>
|
||||
#include <libssh/callbacks.h>
|
||||
#include <pthread.h>
|
||||
#include <threads.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#ifdef HAVE_ARGP_H
|
||||
#include <argp.h>
|
||||
#endif
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
#ifndef BUF_SIZE
|
||||
#define BUF_SIZE 2049
|
||||
#endif
|
||||
|
||||
#ifndef KEYS_FOLDER
|
||||
#ifdef _WIN32
|
||||
#define KEYS_FOLDER
|
||||
#else
|
||||
#define KEYS_FOLDER "/etc/ssh/"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define USER "myuser"
|
||||
#define PASSWORD "mypassword"
|
||||
|
||||
|
||||
|
||||
static int authenticated=0;
|
||||
static int tries = 0;
|
||||
static int error = 0;
|
||||
static ssh_channel chan[30] ={NULL};
|
||||
|
||||
typedef struct {
|
||||
ssh_session session;
|
||||
int id;
|
||||
} ud;
|
||||
|
||||
static int auth_none(ssh_session session,
|
||||
const char *user,
|
||||
void *userdata)
|
||||
{
|
||||
ssh_string banner = NULL;
|
||||
|
||||
(void)user; /* unused */
|
||||
(void)userdata; /* unused */
|
||||
|
||||
//ssh_set_auth_methods(session,
|
||||
// SSH_AUTH_METHOD_PASSWORD | SSH_AUTH_METHOD_GSSAPI_MIC);
|
||||
|
||||
banner = ssh_string_from_char("Loggin To your skelvetty acount!\n");
|
||||
if (banner != NULL) {
|
||||
ssh_send_issue_banner(session, banner);
|
||||
}
|
||||
ssh_string_free(banner);
|
||||
|
||||
authenticated ++;
|
||||
return SSH_AUTH_SUCCESS;
|
||||
}
|
||||
|
||||
static int auth_password(ssh_session session, const char *user,
|
||||
const char *password, void *userdata){
|
||||
(void)userdata;
|
||||
printf("Authenticating user %s pwd %s\n",user, password);
|
||||
if(strcmp(user,USER) == 0 && strcmp(password, PASSWORD) == 0){
|
||||
authenticated = 1;
|
||||
printf("Authenticated\n");
|
||||
return SSH_AUTH_SUCCESS;
|
||||
}
|
||||
if (tries >= 3){
|
||||
printf("Too many authentication tries\n");
|
||||
ssh_disconnect(session);
|
||||
error = 1;
|
||||
return SSH_AUTH_DENIED;
|
||||
}
|
||||
tries++;
|
||||
return SSH_AUTH_DENIED;
|
||||
}
|
||||
|
||||
#ifdef WITH_GSSAPI
|
||||
static int auth_gssapi_mic(ssh_session session, const char *user, const char *principal, void *userdata){
|
||||
ssh_gssapi_creds creds = ssh_gssapi_get_creds(session);
|
||||
(void)userdata;
|
||||
printf("Authenticating user %s with gssapi principal %s\n",user, principal);
|
||||
if (creds != NULL)
|
||||
printf("Received some gssapi credentials\n");
|
||||
else
|
||||
printf("Not received any forwardable creds\n");
|
||||
printf("authenticated\n");
|
||||
authenticated = 1;
|
||||
return SSH_AUTH_SUCCESS;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int pty_request(ssh_session session, ssh_channel channel, const char *term,
|
||||
int x,int y, int px, int py, void *userdata){
|
||||
(void) session;
|
||||
(void) channel;
|
||||
(void) term;
|
||||
(void) x;
|
||||
(void) y;
|
||||
(void) px;
|
||||
(void) py;
|
||||
(void) userdata;
|
||||
printf("Allocated terminal\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int shell_request(ssh_session session, ssh_channel channel, void *userdata){
|
||||
(void)session;
|
||||
(void)channel;
|
||||
(void)userdata;
|
||||
printf("Allocated shell\n");
|
||||
return 0;
|
||||
}
|
||||
struct ssh_channel_callbacks_struct channel_cb = {
|
||||
.channel_pty_request_function = pty_request,
|
||||
.channel_shell_request_function = shell_request
|
||||
};
|
||||
|
||||
static ssh_channel new_session_channel(ssh_session session, void *userdata){
|
||||
(void) session;
|
||||
(void) userdata;
|
||||
printf("Allocated session channel for id %d\n", *(int*)userdata);
|
||||
*(ssh_channel*)userdata = ssh_channel_new(session);
|
||||
ssh_callbacks_init(&channel_cb);
|
||||
ssh_set_channel_callbacks(*(ssh_channel*)userdata, &channel_cb);
|
||||
return *(ssh_channel*)userdata;
|
||||
}
|
||||
|
||||
|
||||
#ifdef HAVE_ARGP_H
|
||||
const char *argp_program_version = "libssh server example "
|
||||
SSH_STRINGIFY(LIBSSH_VERSION);
|
||||
const char *argp_program_bug_address = "<libssh@libssh.org>";
|
||||
|
||||
/* Program documentation. */
|
||||
static char doc[] = "libssh -- a Secure Shell protocol implementation";
|
||||
|
||||
/* A description of the arguments we accept. */
|
||||
static char args_doc[] = "BINDADDR";
|
||||
|
||||
/* The options we understand. */
|
||||
static struct argp_option options[] = {
|
||||
{
|
||||
.name = "port",
|
||||
.key = 'p',
|
||||
.arg = "PORT",
|
||||
.flags = 0,
|
||||
.doc = "Set the port to bind.",
|
||||
.group = 0
|
||||
},
|
||||
{
|
||||
.name = "hostkey",
|
||||
.key = 'k',
|
||||
.arg = "FILE",
|
||||
.flags = 0,
|
||||
.doc = "Set the host key.",
|
||||
.group = 0
|
||||
},
|
||||
{
|
||||
.name = "rsakey",
|
||||
.key = 'r',
|
||||
.arg = "FILE",
|
||||
.flags = 0,
|
||||
.doc = "Set the rsa key (deprecated alias for 'k').",
|
||||
.group = 0
|
||||
},
|
||||
{
|
||||
.name = "verbose",
|
||||
.key = 'v',
|
||||
.arg = NULL,
|
||||
.flags = 0,
|
||||
.doc = "Get verbose output.",
|
||||
.group = 0
|
||||
},
|
||||
{
|
||||
.name = "config",
|
||||
.key = 'f',
|
||||
.arg = "FILE",
|
||||
.flags = 0,
|
||||
.doc = "Configuration file to use.",
|
||||
.group = 0
|
||||
},
|
||||
{NULL, 0, NULL, 0, NULL, 0}
|
||||
};
|
||||
|
||||
/* Parse a single option. */
|
||||
static error_t parse_opt (int key, char *arg, struct argp_state *state) {
|
||||
/* Get the input argument from argp_parse, which we
|
||||
* know is a pointer to our arguments structure.
|
||||
*/
|
||||
ssh_bind sshbind = state->input;
|
||||
|
||||
switch (key) {
|
||||
case 'p':
|
||||
ssh_bind_options_set(sshbind, SSH_BIND_OPTIONS_BINDPORT_STR, arg);
|
||||
break;
|
||||
case 'r':
|
||||
case 'k':
|
||||
ssh_bind_options_set(sshbind, SSH_BIND_OPTIONS_HOSTKEY, arg);
|
||||
break;
|
||||
case 'v':
|
||||
ssh_bind_options_set(sshbind, SSH_BIND_OPTIONS_LOG_VERBOSITY_STR, "3");
|
||||
break;
|
||||
case 'f':
|
||||
ssh_bind_options_parse_config(sshbind, arg);
|
||||
break;
|
||||
case ARGP_KEY_ARG:
|
||||
if (state->arg_num >= 1) {
|
||||
/* Too many arguments. */
|
||||
argp_usage (state);
|
||||
}
|
||||
ssh_bind_options_set(sshbind, SSH_BIND_OPTIONS_BINDADDR, arg);
|
||||
break;
|
||||
case ARGP_KEY_END:
|
||||
if (state->arg_num < 1) {
|
||||
/* Not enough arguments. */
|
||||
argp_usage (state);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return ARGP_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Our argp parser. */
|
||||
static struct argp argp = {options, parse_opt, args_doc, doc, NULL, NULL, NULL};
|
||||
#endif /* HAVE_ARGP_H */
|
||||
|
||||
void* Handel_Client(void* d) {
|
||||
ud data = *(ud*)d;
|
||||
char buf[BUF_SIZE];
|
||||
int r;
|
||||
int i;
|
||||
ssh_event mainloop;
|
||||
ssh_session session = data.session;
|
||||
ssh_channel c;
|
||||
|
||||
struct ssh_server_callbacks_struct cb = {
|
||||
.userdata = (void*)&c,
|
||||
.auth_none_function = auth_none,
|
||||
.auth_password_function = auth_password,
|
||||
.channel_open_request_session_function = new_session_channel,
|
||||
};
|
||||
|
||||
ssh_callbacks_init(&cb);
|
||||
ssh_set_server_callbacks(session, &cb);
|
||||
|
||||
if (ssh_handle_key_exchange(session)) {
|
||||
printf("ssh_handle_key_exchange: %s\n", ssh_get_error(session));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ssh_set_auth_methods(session, SSH_AUTH_METHOD_NONE);
|
||||
|
||||
mainloop = ssh_event_new();
|
||||
ssh_event_add_session(mainloop, session);
|
||||
|
||||
while (!(authenticated && c != NULL)){
|
||||
if(error)
|
||||
break;
|
||||
r = ssh_event_dopoll(mainloop, -1);
|
||||
if (r == SSH_ERROR){
|
||||
printf("Error : %s\n",ssh_get_error(session));
|
||||
ssh_disconnect(session);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
char sendBuf[1024] = {0};
|
||||
int counter = 0;
|
||||
if(error){
|
||||
printf("Error, exiting loop\n");
|
||||
} else
|
||||
printf("Authenticated and got a channel\n");
|
||||
// GameInit()
|
||||
do{
|
||||
i = 1;
|
||||
snprintf(sendBuf, 1024, "Counter: %d, id: %d\r", counter, data.id);
|
||||
char kittyBuffer[30] = {0};
|
||||
sprintf(kittyBuffer, "\e[>%d", 0b1000);
|
||||
if (ssh_channel_write(c, kittyBuffer, 30) == SSH_ERROR) {
|
||||
printf("error writing to channel\n");
|
||||
return NULL;
|
||||
}
|
||||
i = ssh_channel_read_nonblocking(c, buf, sizeof(buf)-1, 0);
|
||||
counter++;
|
||||
// code go here
|
||||
// GameUpdate()
|
||||
// code go here
|
||||
if (ssh_channel_write(c, sendBuf, 1024) == SSH_ERROR) {
|
||||
printf("error writing to channel\n");
|
||||
return NULL;
|
||||
}
|
||||
if(i>0) {
|
||||
|
||||
buf[i] = '\0';
|
||||
printf("%s", buf);
|
||||
fflush(stdout);
|
||||
if(buf[0] == '\x03') {
|
||||
ssh_disconnect(data.session);
|
||||
ssh_free(data.session);
|
||||
authenticated--;
|
||||
//ssh_channel_close(c);
|
||||
//ssh_channel_free(c);
|
||||
return 0;
|
||||
}
|
||||
|
||||
//if (buf[0] == '\x0d') {
|
||||
// if (ssh_channel_write(chan, "\n", 1) == SSH_ERROR) {
|
||||
// printf("error writing to channel\n");
|
||||
// return 1;
|
||||
// }
|
||||
|
||||
// printf("\n");
|
||||
//}
|
||||
}
|
||||
} while (true);
|
||||
|
||||
return 0;
|
||||
}
|
||||
int main(int argc, char **argv){
|
||||
ssh_session session;
|
||||
ssh_bind sshbind;
|
||||
|
||||
int port = 2222;
|
||||
int r =0;
|
||||
|
||||
sshbind=ssh_bind_new();
|
||||
|
||||
ssh_bind_options_set(sshbind, SSH_BIND_OPTIONS_HOSTKEY, "./rsa.key");
|
||||
ssh_bind_options_set(sshbind, SSH_BIND_OPTIONS_BINDPORT, &port);
|
||||
//ssh_bind_set_blocking(sshbind, 0);
|
||||
|
||||
#ifdef HAVE_ARGP_H
|
||||
/*
|
||||
* Parse our arguments; every option seen by parse_opt will
|
||||
* be reflected in arguments.
|
||||
*/
|
||||
argp_parse (&argp, argc, argv, 0, 0, sshbind);
|
||||
#else
|
||||
(void) argc;
|
||||
(void) argv;
|
||||
#endif
|
||||
|
||||
while(sshbind) {
|
||||
|
||||
if(ssh_bind_listen(sshbind)<0){
|
||||
printf("Error listening to socket: %s\n",ssh_get_error(sshbind));
|
||||
return 1;
|
||||
}
|
||||
session=ssh_new();
|
||||
r=ssh_bind_accept(sshbind,session);
|
||||
if(r==SSH_ERROR){
|
||||
printf("error accepting a connection : %s\n",ssh_get_error(sshbind));
|
||||
return 1;
|
||||
}
|
||||
ud d = {session, authenticated};
|
||||
|
||||
pthread_t thread_id;
|
||||
if(pthread_create(&thread_id, NULL, Handel_Client, (void*)&d) < 0) {
|
||||
ssh_disconnect(session);
|
||||
}
|
||||
}
|
||||
// GameEnd()
|
||||
//ssh_disconnect(session);
|
||||
//ssh_bind_free(sshbind);
|
||||
//ssh_finalize();
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user