⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 hclecho.cpp

📁 伯克利做的SFTP安全文件传输协议
💻 CPP
字号:
// hclecho.cpp// a Hummingbird inetd-compatible echo server// copyright SafeTP Development Group, Inc., 2000  Terms of use are as specified in license.txt#include <stdio.h>      // perror, FILE fns#include <errno.h>      // _sys_errlist#include <stdlib.h>     // exit#include <string.h>     // strcpy, strlen#include <dir.h>        // getcwd#include <ctype.h>      // isdigit#include "minwin.h"     // api#include <winsock.h>    // SOCKET#include <winreg.h>     // registry stuff//#include "hcllib.h"     // InitInetd, ShutdownInetd#include "syserr.h"     // xsyserror// global log fileFILE *log = NULL;// this differs from xsyserror in that this fn returns (while// xsyserror throws an exception)void sockerr(char const *msg){  fprintf(log, "%s\n", (char const*)sysErrorString(msg));}void sockerrcode(char const *msg, int code){  fprintf(log, "%s\n", (char const*)sysErrorCodeString(code, msg));}// more hackingHINSTANCE getInstance(){  return (HINSTANCE)GetModuleHandle(NULL);}// what I eventually want to wrap in its own moduleSOCKET inetdStartupHook(int &argc, char **&argv){  // first, test to see if we've been started under HCL inetd  if (!( argc > 1 && isdigit(argv[1][0]) )) {    // the first character is always a digit under HCL inetd, and    // since it was not in this case, we are not running under HCL inetd    return INVALID_SOCKET;  }  // try to load the DLL that communicates with the inetd server  HINSTANCE hHCLDLLInst = LoadLibrary("HCLLIB.DLL");  if (hHCLDLLInst == NULL) {    xsyserror("LoadLibrary",              "couldn't load HCLLIB.DLL, required for HCL inetd operation.");  }  // get a pointer to the function we need  typedef SOCKET (*LPDLLInitInetd)(LPSTR lpszCmdLine);  LPDLLInitInetd DLLInitInetd;  DLLInitInetd = (LPDLLInitInetd)GetProcAddress(hHCLDLLInst, "DLLInitInetd");  if (!DLLInitInetd) {    xsyserror("GetProcAddress",              "trying to get address of DLLInitInetd from HCLLIB.DLL");  }  // get the acceptance socket  SOCKET socket;  socket = DLLInitInetd(argv[1]);    // This must be the command line passed    // to the daemon application or argv[1]    // for console applications.    // On return lpszCmdLine will have    // The optional parameters as specified    // in Inetd.    // SM: Since we're passing argv[1], inetd will toast it (no    //     big deal), and we'll increment argv on return (and assume    //     the caller won't try to read argv[0] as its executable name).    // SM: I just noticed that DLLInitInetd returns SOCKET_ERROR instead    //     of INVALID_SOCKET on error.. that's a mistake on the part of    //     the interface designer, because technically SOCKET_ERROR is    //     in the range of valid socket descriptors (whereas    //     INVALID_SOCKET is not).    // SM: Turns out they're the same... oh well.  if (socket == SOCKET_ERROR) {    // this is not just a simple failure to run under inetd, because    // we already detected that the first argument was numeric    xfailure("DLLInitInetd claims not to recognize my first argument.. "             "did you specify a numeric first argument by mistake?");  }  // having successfully processed the first argument, adjust argc  // and argv so it looks like it wasn't there at all (note that this  // is slightly problematic, in that argv[0], which wasn't involved  // at all, has now effectively been clobbered)  argc--;  argv++;  // put socket in blocking mode  {    // we need a dummy window handle...    HWND dummyWindow = CreateWindow(      "STATIC",	// address of registered class name      "",	// address of window name      WS_OVERLAPPED,	// window style      0,	// horizontal position of window      0,	// vertical position of window      0,	// window width      0,	// window height      NULL,	// handle of parent or owner window      NULL,	// handle of menu or child-window identifier      getInstance(),	// handle of application instance      NULL 	// address of window-creation data    );    if (!dummyWindow) {      xsyserror("CreateWindow", "making a dummy window");    }    // must "reset" WSAAsyncSelect first, it appears    if (0 != WSAAsyncSelect(socket, dummyWindow, 0,0)) {      xsyserror("WSAAsyncSelect");    }    // do the damned mode change    unsigned long blockmode = 0;    if (0 != ioctlsocket(socket, FIONBIO, &blockmode)) {      xsyserror("ioctlsocket");    }    // get rid of the dummy window    if (!DestroyWindow(dummyWindow)) {      sockerr("DestroyWindow");      // continue anyway    }  }  // ok, we're in business  return socket;}int entry(int argc, char *argv[]){  // try to log stuff  FILE *log = fopen("d:\\temp\\hclecho.log", "a");//  FILE *log = fopen("c:\\sftpd\\hclecho\\hclecho.log", "a");  if (!log) {    // cause a distinguished segfault (I'm sure to see it)    *((char*)0xabcd0001) = 0;  }  // log initial arguments  {    fprintf(log, "echo server started, arguments:");    loopi(argc) {      fprintf(log, " %s", argv[i]);    }    fprintf(log, "\n");  }  // who am i?  {    char buf[80];    DWORD buflen=80;    if (!GetUserName(buf, &buflen)) {      sockerr("GetUserName");    }    fprintf(log, "user name is \"%s\"\n", buf);  }  // where am I?  {    char buf[80];    if (!getcwd(buf, 80)) {      sockerr("getcwd");    }    else {      fprintf(log, "getcwd returned \"%s\"\n", buf);    }  }  // try to access a protected registry key  {    DWORD err;    #define CKERR(msg)                  \      if (err != ERROR_SUCCESS) {       \        sockerrcode(msg, err);          \        break;                          \      }    HKEY hkey = NULL;    do {      // open the Protected key      // (assumption: hkey is unchanged when RegOpenKeyEx fails)      // the return value for 'access denied' is 5      err = RegOpenKeyEx(        HKEY_LOCAL_MACHINE,	// handle of open key        "SOFTWARE\\UCB\\SafeTP\\Protected",	// address of name of subkey to open        0,	// reserved        KEY_ALL_ACCESS,	// security access mask        &hkey 	// address of handle of open key      );      CKERR("RegOpenKeyEx");      // read something      // (on my system, I created the 'secret' value in regedit)      DWORD type;      char buf[80];      DWORD buflen = 80;      err = RegQueryValueEx(        hkey,	// handle of key to query        "secret",	// address of name of value to query        NULL,	// reserved        &type,	// address of buffer for value type        buf,	// address of data buffer        &buflen 	// address of data buffer size      );      CKERR("RegQueryValueEx");      fprintf(log, "read \"%s\" from secret value\n", buf);      // write something      strcpy(buf, "hehe, a new secret!");      err = RegSetValueEx(        hkey,	// handle of key to set value for        "writtenSecret",	// address of value to set        0,	// reserved        REG_SZ,	// flag for value type        buf,	// address of value data        strlen(buf) 	// size of value data      );      CKERR("RegSetValueEx");    } while (0);     // above, let 'break' mean 'goto here'    // close the registry key if we successfully opened it    if (hkey != NULL) {      err = RegCloseKey(hkey);      if (err != ERROR_SUCCESS) {        sockerrcode("RegCloseKey", err);      }      else {        fprintf(log, "all registry operations succeeded\n");      }    }    #undef CKERR  }  // WSAStartup MUST be called before InitInetd  {    WSADATA wsdata;    if (0 != WSAStartup(0x0101, &wsdata)) {      sockerr("WSAStartup");      return 1;    }  }  // get the acceptance socket  SOCKET socket = inetdStartupHook(argc, argv);  if (socket == INVALID_SOCKET) {    fprintf(log, "exiting because not run from inetd\n");    MessageBox(NULL, "Must be run from Inetd", "HCL Echo", MB_OK);    return 1;  }  // log final arguments  {    fprintf(log, "final arguments:");    loopi(argc) {      fprintf(log, " %s", argv[i]);    }    fprintf(log, "\n");  }  // do what the echo server does  int charCount = 0;  for (;; charCount++) {    // read a character    char ch;    int len = recv(socket, &ch, 1, 0);    if (len == 0) {      // eof      break;    }    if (len < 0) {      xsyserror("recv");    }    // write that character    len = send(socket, &ch, 1, 0);    if (len != 1) {      xsyserror("recv");    }  }  if (0 != closesocket(socket)) {    sockerr("closesocket");  }  if (0 != WSACleanup()) {    sockerr("WSACleanup");  }  fprintf(log, "done, echoed %d characters\n", charCount);  fclose(log);  return 0;}int main(int argc, char *argv[]){  try {    return entry(argc, argv);  }  catch (xBase &x) {    printf("Exception caught: %s\n", x.why());    WSACleanup();    return 4;  }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -