Ejemplo n.º 1
0
// read configuration either from INI file (if it exists) or from the registry
int DHCPReadConfig ( )
{
int   Ark;
char szBuf[128];

   memset (& sParamDHCP, 0, sizeof sParamDHCP);
   sParamDHCP.nLease = DHCP_DEFAULT_LEASE_TIME;

   for (Ark=0 ; Ark<SizeOfTab (tDHCPd32Entry) ; Ark++)
        ReadKey (  TFTPD32_DHCP_KEY, 
                   tDHCPd32Entry [Ark].szEntry,
                   tDHCPd32Entry [Ark].pValue,
                   tDHCPd32Entry [Ark].nBufSize,
                   tDHCPd32Entry [Ark].nType,
                   szTftpd32IniFile );
    // custom items
   for (Ark=0 ; Ark < SizeOfTab (sParamDHCP.t) ; Ark++)
   {
      wsprintf (szBuf, "%s%d", KEY_DHCP_USER_OPTION_NB, Ark+1);
      ReadKey  (TFTPD32_DHCP_KEY, szBuf, & sParamDHCP.t[Ark].nAddOption, 
                sizeof sParamDHCP.t[Ark].nAddOption, REG_DWORD, szTftpd32IniFile);

       wsprintf (szBuf, "%s%d", KEY_DHCP_USER_OPTION_VALUE, Ark+1);
       ReadKey  (TFTPD32_DHCP_KEY,  szBuf, sParamDHCP.t[Ark].szAddOption, 
                 sizeof sParamDHCP.t[Ark].szAddOption, REG_SZ, szTftpd32IniFile);
   }

   if ( sParamDHCP.nPoolSize!=0 )
   {
	  tFirstIP = malloc (sParamDHCP.nPoolSize * sizeof *tFirstIP[0]) ;
	  tMAC = malloc (sParamDHCP.nPoolSize * sizeof *tMAC[0]) ; 
	  if (tFirstIP == NULL  ||  tMAC == NULL ) 
	   {
			SVC_ERROR ("Can not allocate memory");
			return FALSE;
	   }
	   LoadLeases ();
   }

   if (sParamDHCP.nLease==0)
   {  
      sParamDHCP.nLease=DHCP_DEFAULT_LEASE_TIME;
      LOG (12, "%d, Lease time not specified, set to 2 days", GetCurrentThreadId ());
   }
   // compatability 3 -> 4
   if (sParamDHCP.szWins[0]==0  && sParamDHCP.szDns1[0]!=0)
   {
      lstrcpy (sParamDHCP.szWins, sParamDHCP.szDns1);
      LOG (0, "WINS server copied from DNS servers");
   }

return TRUE;
} // DHCPReadConfig
Ejemplo n.º 2
0
/////////////////////////////////////////
// Dir window callback
LRESULT CALLBACK ShDirProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
static const int tTabs[] = { 90, 125 };
struct S_DirectoryContent *pDir = (struct S_DirectoryContent *) lParam;
HWND hLBWnd = GetDlgItem (hWnd, IDC_LB_SHDIR);
int Ark;

  switch (message)
  {
       case WM_INITDIALOG :
	   	   // Set the window name to either tftpd32 or tftpd64
	       SetWindowText (hWnd, TFTPD_DIR_TITLE);

           ListBox_SetTabStops ( hLBWnd, SizeOfTab(tTabs), tTabs );
           ListBox_ResetContent ( hLBWnd );
           for ( Ark=0 ;  Ark < pDir->nb ;  Ark++ )
                ListBox_AddString ( hLBWnd, pDir->ent[Ark].file_descr );
           CenterChildWindow (hWnd, CCW_INSIDE | CCW_VISIBLE);
           // If GUI is in remote mode, deactivate Explorer Button
           if ( IsGuiConnectedToRemoteService () )
                Button_Enable (GetDlgItem (hWnd, IDC_SD_EXPLORER), FALSE);
           break;

       case WM_COMMAND :
            Handle_VM_Command (hWnd, wParam, lParam);
           break;
       case WM_CLOSE :
       case WM_DESTROY :
            EndDialog (hWnd, 0);
            break;

  } // switch

return FALSE;
} // ShDirProc
Ejemplo n.º 3
0
/////////////////////////////////////////////////////////
// Read settings :
// Parse the settings table and call ReadKey
/////////////////////////////////////////////////////////
BOOL Tftpd32ReadSettings (void)
{
int Ark, Rc=TRUE;
char szCurDir[_MAX_PATH];
   for (Ark=0 ;   Ark< SizeOfTab (tTftpd32Entry) ;   Ark++)
     ReadKey (   TFTPD32_MAIN_KEY, 
                 tTftpd32Entry[Ark].szEntry,
                 tTftpd32Entry[Ark].pValue,
                 tTftpd32Entry[Ark].nBufSize,
                 tTftpd32Entry[Ark].nType,
                 szTftpd32IniFile );
  if (sSettings.uServices == TFTPD32_NONE)  sSettings.uServices = TFTPD32_ALL_SERVICES;
  
    // field WorkingDirectory : 
    // try env variable then szBaseDir and current dir
    if (    GetEnvironmentVariable (TFTP_DIR, szCurDir, sizeof szCurDir) != 0 
         && IsValidDirectory ( szCurDir ) )
                GetFullPathName ( szCurDir, 
                                  sizeof sSettings.szWorkingDirectory,
                                  sSettings.szWorkingDirectory, 
                                  NULL );
    else if ( IsValidDirectory ( sSettings.szBaseDirectory ) )
                GetFullPathName ( sSettings.szBaseDirectory, 
                                  sizeof sSettings.szWorkingDirectory,
                                  sSettings.szWorkingDirectory, 
                                  NULL );
    else        GetCurrentDirectory ( sizeof sSettings.szWorkingDirectory,
                                       sSettings.szWorkingDirectory );
// release for the Australian Department of defence
#ifdef BAE_SYSTEMS_LEN_WHITE
  sSettings.uServices = TFTPD32_TFTP_SERVER;
#endif
return Rc;
} // Tftpd32ReadSettings
Ejemplo n.º 4
0
///////////////////////////////////////////////
// Tab control has changed : hide/show controls
LRESULT TR_ChangeTabControl (HWND hDlgWnd)
{
HWND   hTabWnd = GetDlgItem (hDlgWnd, IDC_TAB_OPTION);
DWORD  nCurOnglet = TabCtrl_GetCurSel (hTabWnd);
DWORD  Ark;
DWORD  TabMask;
TC_ITEM TabCtrlItem;

 // get the selected tab id
 if (nCurOnglet != (DWORD)-1)
   {
          TabCtrlItem.mask = TCIF_PARAM   ;
          TabCtrl_GetItem (hTabWnd, nCurOnglet, & TabCtrlItem);
          TabMask = MakeMask (TabCtrlItem.lParam);
   }
  else    TabMask = TAB_NONE;

 // according to TabMask and tResize table hide/display controls
 for (Ark=0 ; Ark<SizeOfTab(tResize) ; Ark++)
        ShowWindow (GetDlgItem (hDlgWnd, tResize[Ark].idCtrl),
                    (tResize[Ark].mView & TabMask) ? SW_SHOW : SW_HIDE);

  // DHCP tab has been selected : display the settings
  if (TabMask == TAB_DHCP_SERVER)
  {
	 Gui_LoadDHCPConfig (hDlgWnd);
  }

return TabCtrlItem.lParam ;
} // ChangeTabControl
Ejemplo n.º 5
0
// Save configuration either in INI file (if it exists) or in registry
int DHCPSaveConfig ( const struct S_DHCP_Param  *pNewParamDHCP )
{
INT   Ark;
char szBuf[64];

     // allocate new array, but keep pointers
     if ( sParamDHCP.nPoolSize!=pNewParamDHCP->nPoolSize )
	 {
         tFirstIP = realloc (tFirstIP, sizeof (tFirstIP[0]) * pNewParamDHCP->nPoolSize);
         tMAC     = realloc (tMAC,     sizeof (tMAC[0]) * pNewParamDHCP->nPoolSize);
		      // do not complain if pool is empty
         if (pNewParamDHCP->nPoolSize!=0 && (tFirstIP==NULL || tMAC==NULL) )
		{
			SVC_ERROR ("Can not allocate memory");
			return FALSE;
		}
	 }
     
     nAllocatedIP = min (nAllocatedIP, pNewParamDHCP->nPoolSize);

     sParamDHCP = *pNewParamDHCP;

     for (Ark=0 ; Ark<SizeOfTab (tDHCPd32Entry) ; Ark++)
        AsyncSaveKey (  TFTPD32_DHCP_KEY,
                        tDHCPd32Entry [Ark].szEntry,
                        tDHCPd32Entry [Ark].pValue,
                        tDHCPd32Entry [Ark].nBufSize,
                        tDHCPd32Entry [Ark].nType,
                        szTftpd32IniFile );
 
 // custom items
    for (Ark=0 ; Ark < SizeOfTab (sParamDHCP.t) ; Ark++)
    {
       wsprintf (szBuf, "%s%d", KEY_DHCP_USER_OPTION_NB, Ark+1);
       AsyncSaveKey  (TFTPD32_DHCP_KEY, szBuf, & sParamDHCP.t[Ark].nAddOption,
                 sizeof sParamDHCP.t[Ark].nAddOption, REG_DWORD, szTftpd32IniFile);
       wsprintf (szBuf, "%s%d", KEY_DHCP_USER_OPTION_VALUE, Ark+1);
       AsyncSaveKey  (TFTPD32_DHCP_KEY,  szBuf, sParamDHCP.t[Ark].szAddOption,
                 sizeof sParamDHCP.t[Ark].szAddOption, REG_SZ, szTftpd32IniFile);
    }

return TRUE;
} // DHCPSaveConfig
Ejemplo n.º 6
0
///////////////////////////////////////////////
// Resize the main window --> resize each control
int TR_ResizeWindow (HWND hDlgWnd, BOOL bInit)
{
static BOOL bConvert2Physique=FALSE;
DWORD Ark;
RECT  RClient;
SIZE  SClient;
int  InflateX, InflateY;       // tenth

 // at first call : convert logical data to physical
  if (! bConvert2Physique)
  {
      bConvert2Physique = TRUE;
      for (Ark=0 ; Ark<SizeOfTab(tResize) ; Ark++)
           MapDialogRect (hDlgWnd, (LPRECT) & tResize[Ark].x);
      MapDialogRect (hDlgWnd, & SizeInit);
      MapDialogRect (hDlgWnd, & RectMinMax);
      MapDialogRect (hDlgWnd, & RectTftpClient);
   } 

  if (bInit)
        MoveWindow (hDlgWnd, SizeInit.left, SizeInit.top, SizeInit.right, SizeInit.bottom, FALSE);

    // get window size and calculate the inflate rate
    GetWindowRect (hDlgWnd, & RClient);
    SClient.cx = RClient.right - RClient.left;
    SClient.cy = RClient.bottom - RClient.top;
    InflateX = 10 * ( SClient.cx - (SizeInit.right - SizeInit.left) );
    InflateY = 10 * ( SClient.cy - (SizeInit.bottom - SizeInit.top) );

    for (Ark=0 ; Ark<SizeOfTab(tResize) ; Ark++)
    {
        MoveWindow (GetDlgItem (hDlgWnd, tResize[Ark].idCtrl),
                    tResize[Ark].x + (tResize[Ark].dx * InflateX) / 100,
                    tResize[Ark].y + (tResize[Ark].dy * InflateY) / 100,
                    tResize[Ark].width + (tResize[Ark].dwidth * InflateX) / 100,
                    tResize[Ark].height+ (tResize[Ark].dheight * InflateY) / 100,
                    TRUE);
    }

    InvalidateRect (hDlgWnd, NULL, FALSE);

return Ark;
} //TR_ResizeWindow
Ejemplo n.º 7
0
/* ----------------------------------------------------- */
int Skt4uInit (void)
{
int Ark;

   if (! bInitDone)  /* Aucune socket ouverte */
     {
       for (Ark=0 ; Ark<SizeOfTab(HistoSocket) ; Ark++)
          HistoSocket[Ark].skt = INVALID_SOCKET;
       bInitDone=TRUE;  
     }
#ifdef WINDOWS
   /* liberation des sockets appartenant a des taches mortes */
   else
    {
       for (Ark=0 ;  Ark<SizeOfTab(HistoSocket) ; Ark++)
     if (      HistoSocket[Ark].skt!=INVALID_SOCKET 
           && !IsTask(HistoSocket[Ark].hTask) )
            TcpClose (& HistoSocket[Ark].skt);
    }  /* InitDone */
#endif
return TCP4U_SUCCESS;
} /* Skt4wInit */
Ejemplo n.º 8
0
/////////////////////////////////////////////////////////
// Save Settings into ini file/registry
/////////////////////////////////////////////////////////
BOOL Tftpd32SaveSettings (void)
{
int Ark, Rc;

   for (Ark=0, Rc=TRUE ; Rc  &&  Ark< SizeOfTab (tTftpd32Entry) ; Ark++)
    Rc = AsyncSaveKey ( TFTPD32_MAIN_KEY, 
                   tTftpd32Entry[Ark].szEntry,                     
                   tTftpd32Entry[Ark].pValue,
                   tTftpd32Entry[Ark].nBufSize, 
                   tTftpd32Entry[Ark].nType,
                   szTftpd32IniFile );
    if (! Rc)  REG_ERROR();
return Rc;

} // Tftpd32SaveSettings
Ejemplo n.º 9
0
/*######################################################################
 *##
 *## NAME:  HttpSendAdditionnalHeader
 *##
 *## PURPOSE: Send a http 1.0 general-header  
 *##
 *####################################################################*/
static int HttpSendAdditionnalHeader(SOCKET CSock)
{
  int Ark;
  int Rc;
  static LPCSTR szAdditionnalStrings[] = 
  {
    "Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, */*",
    "User-Agent: Http4u by Ph. Jounin and L. Le Bras",
    "",
  };

  Tcp4uLog (LOG4U_INTERN, "HttpSendAdditionnalHeader");

  /* sending request,  if successful send Request Header */
  for (Rc=TCP4U_SUCCESS,Ark=0 ; Rc==TCP4U_SUCCESS && Ark<SizeOfTab(szAdditionnalStrings); Ark++)
     Rc = TnSend (CSock, szAdditionnalStrings[Ark], FALSE, DO_NOT_LOG);

return Rc==TCP4U_SUCCESS ?  HTTP4U_SUCCESS :  HTTP4U_TCP_FAILED;
} /* END HttpSendAdditionnalHeader */
Ejemplo n.º 10
0
/* -------------------------------------------------------------- */
int API4U SmtpSendRcpt (SOCKET CSock, LPCSTR szTo, 
                        LPSTR szBuffer, UINT uBufSize)
{
LPCSTR pTo  = szTo;
LPSTR  qCmd = NULL;
int    Rc   = SMTP4U_SUCCESS;
int    Ark;

   Tcp4uLog (LOG4U_PROC, "SmtpSendRcpt");
   while (*pTo!=0  &&  Rc==SMTP4U_SUCCESS)
   {
      /* constructs the beginning of the command */
      Strcpy (szBuffer, SmtpProto[_SMTP4U_RCPTTO].szCmd);
      qCmd = szBuffer + Strlen (SmtpProto[_SMTP4U_RCPTTO].szCmd);
    
      /* get the first recipient from the pTo line */
      for (Ark=0 ;  pTo[Ark]!=0  && pTo[Ark]!=SMTP4U_SEPARATOR ;  Ark++)
            qCmd[Ark] = pTo[Ark];
      qCmd[Ark]=0;

      /* skip spaces and affect pTo the next recipient */
      while (pTo[Ark]==SMTP4U_SEPARATOR  || pTo[Ark]==' ' ||  pTo[Ark]=='\t')
                Ark++;
      pTo += Ark;

      /* send the RCPT string */
      Rc = TnProtoExchange (CSock,     /* used socket */
                            szBuffer,
                            szBuffer, uBufSize, 
                            TnReadMultiLine, /* recv function */
                            SmtpProto[_SMTP4U_RCPTTO].tAnswer, 
                            SizeOfTab(SmtpProto[_SMTP4U_RCPTTO].tAnswer),
                            TRUE,      /* sensitive compare */
                            SMTP4U_DEFTIMEOUT, 
                            HFILE_ERROR);
   } /* until either error or no more recipient */
   Tcp4uLog (LOG4U_EXIT, "SmtpSendRcpt");
return  Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc ;
} /* SmtpSendRcpt */
Ejemplo n.º 11
0
/* ------------------------------------------------------------------ */
int Skt4uCleanup (void)
{
int Ark;

   if (bInitDone)
     {
       /* blocking call ? */
       if (WSAIsBlocking())  
        {
           WSACancelBlockingCall (); 
           return TCP4U_ERROR; 
         }
       else 
        {
          /* TcpClose (&s) force s a -1 -> pas besoin de UnrcdSkt */
          for (Ark=0 ; Ark<SizeOfTab(HistoSocket) ; Ark++)
             if (    HistoSocket[Ark].hTask == GetCurrentTask () 
                  && HistoSocket[Ark].skt   != INVALID_SOCKET )
                  TcpClose (& HistoSocket[Ark].skt);  
          WSACleanup ();
        }  /* requete non bloquante */ 
     } /* bInitDone */
return TCP4U_SUCCESS;
} /* Skt4wCleanup */
Ejemplo n.º 12
0
/* ------------------------------------------------------------------ */
static int FindSocketIdx (SOCKET s)
{
int Ark;
   for (Ark=0 ; Ark<SizeOfTab(HistoSocket) && s!=HistoSocket[Ark].skt ; Ark++);
return  Ark<SizeOfTab(HistoSocket) ?  Ark : INVALID_INDEX;
}  /* FindSocketIdx */
Ejemplo n.º 13
0
//////////////////////////////////////////////////////////////////////////////////////////////
// fill DHCP fields
//////////////////////////////////////////////////////////////////////////////////////////////
int DHCPOptionsReply (struct dhcp_packet  *pDhcpPkt, int nDhcpType)
{
unsigned char  *pOpt = (unsigned char *) (pDhcpPkt->options + (sizeof DHCP_OPTIONS_COOKIE - 1));
HANDLE            hFile;
struct in_addr *pNearest;
int             Ark, Evan;
char            sz[256];
static struct S_DhcpOptions sDhcpOpt [] =       // 0 for unspecified
{
    DHO_DHCP_MESSAGE_TYPE,      1,	  ~TFTPD32_NONE,
    DHO_DHCP_SERVER_IDENTIFIER, 4,	  ~TFTPD32_NONE,
    DHO_SUBNET_MASK,            4,	  ~TFTPD32_NONE,
    DHO_ROUTERS,                4,	  ~TFTPD32_NONE,
    DHO_DOMAIN_NAME_SERVERS,    4,	  ~TFTPD32_NONE,
    DHO_LOG_SERVERS,            4,	   TFTPD32_SYSLOG_SERVER,
    DHO_NETBIOS_NAME_SERVERS,   4,	  ~TFTPD32_NONE,
    DHO_DHCP_LEASE_TIME,        4,	  ~TFTPD32_NONE,
    DHO_DHCP_RENEWAL_TIME,      4,	  ~TFTPD32_NONE,
    DHO_DHCP_REBINDING_TIME,    4,	  ~TFTPD32_NONE,
    DHO_BOOT_SIZE,              0,	   TFTPD32_TFTP_SERVER,
    DHO_DOMAIN_NAME,            0,	  ~TFTPD32_NONE,
    DHO_CUSTOM,                 0,	  ~TFTPD32_NONE,
    DHO_END,                    0,	  ~TFTPD32_NONE,
};

	//Always pack the magic cookie again, just in case it was corrupted
	*(DWORD*)(pDhcpPkt->options) = * (DWORD*) DHCP_OPTIONS_COOKIE;

	// pNearest points on the "good" LAN interface
   pNearest = FindNearestServerAddress (&pDhcpPkt->yiaddr, & sParamDHCP.dwMask, FALSE);
   //HACK -- If we are the bootp server, we are also the tftpserver
   if (sSettings.uServices & TFTPD32_TFTP_SERVER) 
      pDhcpPkt->siaddr = *pNearest;   // Next server (TFTP server is enabled)
   for (Ark=0 ; Ark<SizeOfTab(sDhcpOpt) ; Ark++)
   {
	 // skip if linked to a service which is not started (change suggested by Colin)
	 if (! (sSettings.uServices & sDhcpOpt[Ark].nServices)) 
			continue;

     if (sDhcpOpt[Ark].nLen!=0) 
     {
        *pOpt++ = (unsigned char) sDhcpOpt[Ark].nDHCPOpt ; 
        *pOpt++ = (unsigned char) sDhcpOpt[Ark].nLen;
      }
      switch (sDhcpOpt[Ark].nDHCPOpt)
      {
       case DHO_DHCP_MESSAGE_TYPE       :  * pOpt = (unsigned char) nDhcpType ; break ; 
       case DHO_LOG_SERVERS             :  // fallthrough
       case DHO_DHCP_SERVER_IDENTIFIER  :  * (DWORD *) pOpt = pNearest->s_addr; break ;
       case DHO_SUBNET_MASK             :  * (DWORD *) pOpt = sParamDHCP.dwMask.s_addr; break ;
       case DHO_ROUTERS                 :  * (DWORD *) pOpt = (sParamDHCP.dwGateway.s_addr == 0xffffffff ? pDhcpPkt->yiaddr.s_addr : sParamDHCP.dwGateway.s_addr); break ;
       case DHO_NETBIOS_NAME_SERVERS    :
       case DHO_DOMAIN_NAME_SERVERS     :  * (DWORD *) pOpt = sParamDHCP.dwDns.s_addr;  break; 
       case DHO_DHCP_LEASE_TIME         :  * (DWORD *) pOpt = htonl (sParamDHCP.nLease * 60);  break ;
       case DHO_DHCP_RENEWAL_TIME       :
       case DHO_DHCP_REBINDING_TIME     :  * (DWORD *) pOpt = htonl (sParamDHCP.nLease/2 * 60);  break ;
       case DHO_BOOT_SIZE               :
              // translate $IP$ and $MAC$ from boot file name
              TranslateExp (sParamDHCP.szBootFile, sz, pDhcpPkt->yiaddr, pDhcpPkt->chaddr);
              hFile = CreateFile(sz,        // open the file
                                 GENERIC_READ,                 // open for reading
                                 FILE_SHARE_READ,              // share for reading
                                 NULL,                         // no security
                                 OPEN_EXISTING,                // existing file only
                                 FILE_ATTRIBUTE_NORMAL,       // normal file
                                 NULL);                       // no attr. template
               if (hFile != INVALID_HANDLE_VALUE)
               {
                  *pOpt++ = DHO_BOOT_SIZE ;
                  *pOpt++ = sizeof (unsigned short);
                  * (unsigned short *) pOpt = htons ( (unsigned short) (1+GetFileSize (hFile, NULL) / 512) ) ;
                  pOpt += sizeof (unsigned short);
                  CloseHandle( hFile ) ;         // close the file
               }
              break;
        case DHO_DOMAIN_NAME             :
             if (sParamDHCP.szDomainName[0]!=0)
             {
                  *pOpt++ = DHO_DOMAIN_NAME;
                  *pOpt   = lstrlen (sParamDHCP.szDomainName);
                   memcpy (pOpt+1, sParamDHCP.szDomainName, *pOpt);
                   pOpt += 1+*pOpt; 
              }
              break;
     case DHO_CUSTOM : // Manage custom options
         for (Evan=0 ; Evan < SizeOfTab (sParamDHCP.t) ; Evan++)
                if (sParamDHCP.t[Evan].nAddOption != 0)
                {
                   *pOpt++ = (unsigned char) sParamDHCP.t[Evan].nAddOption;
				   *pOpt = TranslateParam2Value (pOpt+1, 64, sParamDHCP.t[Evan].szAddOption, pDhcpPkt->yiaddr, pDhcpPkt->chaddr);
                   pOpt += 1+*pOpt;
               }
              break;
     case DHO_END                     : 
                 *pOpt++ = DHO_END;
                 *pOpt++ = DHO_PAD;
                 *pOpt++ = DHO_PAD;
                 break;
       } // switch option
     pOpt += sDhcpOpt[Ark].nLen ;    // points on next field
   } // for all option

return (int) (pOpt - (unsigned char*) pDhcpPkt);
} // DHCPOptionsReply
Ejemplo n.º 14
0
/////////////////////////////
// Fenetre Background gestion des appels TCP
//
LRESULT CALLBACK TftpClientProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
DWORD          nbWrt;
struct tftphdr *tpr, *tps;
time_t            dNow;
int             Ark;
HWND            hCBWnd, hParentWnd;

  time (&dNow);
  switch (message)
  {

    /////////////////////////
    // Message Windows

    case WM_INITCLIENT :
      // only one client transfer available
      hTftpClientSemaphore = CreateSemaphore(NULL, 1, 1, TFTP_CLIENT_SEMAPHORE);

         hTftpClientWnd = hWnd;
        hParentWnd = GetParent (hWnd);
         EnableWindow (GetDlgItem (hParentWnd, IDC_CLIENT_BREAK_BUTTON), FALSE);
         SetDlgItemText (hParentWnd, IDC_CLIENT_BLOCK, "");

       // populate combo with proposed block sizes
        hCBWnd = GetDlgItem (hParentWnd, IDC_CB_DATASEG);
      for (Ark=0 ;  Ark<SizeOfTab (tBlkSize); Ark++)
                ComboBox_AddString (hCBWnd, tBlkSize[Ark].szBlkSize);
       ComboBox_SetCurSel (hCBWnd, 0);

       // uncheck "Send full path to server"
      SendDlgItemMessage (hParentWnd, IDC_CLIENT_FULL_PATH, BM_SETCHECK, BST_UNCHECKED, 0);   

      // edittext IDC_CLIENT_FILE will accept dropped file (works only because it is on the top in Z-Order
       DragAcceptFiles (GetDlgItem (hParentWnd, IDC_CLIENT_LOCALFILE), TRUE);
          // fEditBoxProc = (WNDPROC) SetWindowLong (GetDlgItem (hParentWnd, IDC_CLIENT_LOCALFILE), GWL_WNDPROC, (LONG) TftpClientFileNameProc);
          fEditBoxProc = (WNDPROC) SetWindowLongPtr (GetDlgItem (hParentWnd, IDC_CLIENT_LOCALFILE), GWLP_WNDPROC, (LONG_PTR) TftpClientFileNameProc);
//    SetWindowLong (GetDlgItem (hParentWnd, IDC_CLIENT_FILE), GWL_USERDATA, (LONG) TftpClientFileNameProc);
    SetWindowLongPtr (GetDlgItem (hParentWnd, IDC_CLIENT_LOCALFILE), GWLP_USERDATA, (LONG_PTR) TftpClientFileNameProc);
         break;

    case WM_CLOSE :
LogToMonitor ("GUI: Closing Tftp Client");
         CloseHandle (hTftpClientSemaphore);
         CloseHandle (sTC.hFile);
         closesocket (sTC.s);
         break;

    case WM_COMMAND :
          Handle_VM_Command (hWnd, wParam, lParam);
          break;


    case WM_TIMER :
         KillTimer(hWnd, wParam);
         PostMessage (hWnd, wParam, 0, (LPARAM) -1);    // pour pas confondre
         break;

      //////////////////////
      // Download : fichier envoyé par le serveur
     case WM_CLIENT_DATA :
        // WSAAsyncSelect (sTC.s, hWnd, 0, 0);  A SUPPRIMER
        KillTimer(hWnd, wParam);
        if (sTC.bBreak) return FALSE;
        sTC.nRcvd = 0;
        // On est reveillé par un message reçu
        tpr = (struct tftphdr *) sTC.BufRcv;
        if (WSAGETSELECTEVENT(lParam) == FD_READ)
        {
            if (! UdpRecv ())
                return BadEndOfTransfer ("Error in Recv.\nError code is %d (%s)", WSAGetLastError (), LastErrorText() );
          // parcours des codes retours
          switch (htons (tpr->th_opcode))
            {
              case TFTP_ERROR :
                   return BadEndOfTransfer ("Server stops the transfer.\nError #%d: %s", htons (tpr->th_code), tpr->th_msg);
             case TFTP_OACK :
                    if (sTC.nCount==0) TftpProcessOACK ();
                     break;
                case TFTP_DATA :
                   // a data packet has been received. Check #block
                   if ( htons (tpr->th_block) == (unsigned short) (sTC.nCount+1) )
                    {
                      if (     !WriteFile (sTC.hFile, tpr->th_data, sTC.nRcvd - TFTP_DATA_HEADERSIZE, & nbWrt, NULL)
                          ||  sTC.nRcvd-TFTP_DATA_HEADERSIZE!=nbWrt)
                            return BadEndOfTransfer ("Error in writing file.\nError code is %d (%s)", GetLastError(), LastErrorText());
                       sTC.nCount++;
                       sTC.nRetransmit = 0;
                       // prepare Ack block
                       tps = (struct tftphdr *) sTC.BufSnd;
                       tps->th_opcode = htons (TFTP_ACK),  tps->th_block = htons ((unsigned short) sTC.nCount);
                       sTC.nToSend = TFTP_DATA_HEADERSIZE;
                       // compute MD5
                       MD5Update (& sTC.m.ctx, tpr->th_data, nbWrt);
                    }
                  break;
             default :
                 return BadEndOfTransfer ("Server sent illegal opcode %d", htons (tpr->th_opcode));
          } // switch opcode
        } // il y a un message à recevoir
        // La comparaison marche si le paquet est le bon ou une répétition du précédent message
        if ( htons (tpr->th_block) == (unsigned short) sTC.nCount)
        {
           if (sTC.nRetransmit)  sTC.nTotRetrans ++;
           if (sTC.nRetransmit++ > TFTP_RETRANSMIT)
                return BadEndOfTransfer ("Timeout waiting block #%d", sTC.nCount+1);
            send (sTC.s, sTC.BufSnd, sTC.nToSend, 0);
            SetTimer (hWnd, WM_CLIENT_DATA, sTC.dwTimeout, NULL);
        }
      // sTC.nRcvd ne peut être inférieur que si on a reçu un block
        if (  htons (tpr->th_opcode)==TFTP_DATA
          &&  sTC.nRcvd!=0
           && sTC.nRcvd < sTC.nPktSize + TFTP_DATA_HEADERSIZE)
                    return TransferOK (dNow);
      Statistics (dNow);
        break;

     ////////////////////////
    // Upload : server sends ACK
     case WM_CLIENT_ACK :
        KillTimer(hWnd, wParam);
       if (sTC.bBreak  ||  sTC.s==INVALID_SOCKET) return FALSE;
       
       // socket not closed by StopTransfer
        tpr = (struct tftphdr *) sTC.BufRcv;
        if ( WSAGETSELECTEVENT(lParam) == FD_READ )
        {
            if (! UdpRecv ())
                return BadEndOfTransfer ("Error in Recv.\nError code is %d (%s)", WSAGetLastError (), LastErrorText() );
            switch (htons (tpr->th_opcode))
            {
              case TFTP_ERROR :
                   return BadEndOfTransfer ("Server stops the transfer.\nError #%d: %s", htons (tpr->th_code), tpr->th_msg);

                case TFTP_OACK :
                    if (sTC.nCount!=0)  break; // ignore message
                   TftpProcessOACK ();
                    tpr->th_block = htons(0);  // pour passer en dessous
                   // Fall through

              case TFTP_ACK :
                    if ( htons (tpr->th_block) == (unsigned short) sTC.nCount )
                    {
                      // prepare Data block
                       tps = (struct tftphdr *) sTC.BufSnd;
                       if ( !ReadFile (sTC.hFile, tps->th_data, sTC.nPktSize, & sTC.nRcvd, NULL) )
                       {
                          if (sTC.nToSend == TFTP_DATA_HEADERSIZE + sTC.nPktSize)  // file was exactly N * PkSize
                                  return TransferOK (dNow);
                            else  return BadEndOfTransfer ("Error in reading file.\nError code is %d (%s)", GetLastError(), LastErrorText());
                       }
                       if (sTC.nRcvd == 0) // EOF 
                        {
                          if (sTC.nToSend < TFTP_DATA_HEADERSIZE + sTC.nPktSize) 
                                return TransferOK (dNow);
                      }
                      sTC.nCount++;
                      sTC.nRetransmit = 0;
                      tps->th_opcode = htons (TFTP_DATA),  tps->th_block = htons ((unsigned short) sTC.nCount);
                      sTC.nToSend = TFTP_DATA_HEADERSIZE + sTC.nRcvd;
                      // compute MD5
                      MD5Update (& sTC.m.ctx, tps->th_data, sTC.nRcvd);
                    }
                  break;
             default :
                   return BadEndOfTransfer ("Server sent illegal opcode %d", htons (tpr->th_opcode));
            } // switch opcode
        } // il y a un message à recevoir

        // Timeout or ack of previous block
        else if ( htons (tpr->th_block) == (unsigned short) (sTC.nCount-1) )
        {
           if (sTC.nRetransmit)  sTC.nTotRetrans ++;
           if (sTC.nRetransmit++ > TFTP_RETRANSMIT)
                return BadEndOfTransfer ("Timeout while waiting ack block #%d", sTC.nCount);
            // une possibilité : on est au dernier message et le serveur TFTP n'a pas acquitté
            // --> on renvoie, mais sur Timeout, on signale un transfert OK
            if (sTC.nToSend < TFTP_DATA_HEADERSIZE + sTC.nPktSize  &&  sTC.nRetransmit<TFTP_RETRANSMIT)
                return TransferOK (dNow);
        }

        send (sTC.s, sTC.BufSnd, sTC.nToSend, 0);
        SetTimer (hWnd, WM_CLIENT_ACK, sTC.dwTimeout, NULL);
      Statistics (dNow);
        break;
   } // switch message

return DefWindowProc (hWnd, message, wParam, lParam);
} // TftpProc
Ejemplo n.º 15
0
///////////////////////////////////////////////
// Initthe Tab control
int TR_InitTabControl (HWND hDlgWnd)
{
TC_ITEM TabCtrlItem;
HWND   hTabWnd = GetDlgItem (hDlgWnd, IDC_TAB_OPTION);
int    nOnglet, Ark;
static const struct S_TabCtrlData
{
	int   tab;
	char *name;
	int   mask;
	int   service;	// TRUE if tab is the GUI of a service
} tTabCtrlData [] =
{
	ONGLET_TFTP_SERVER,   "Tftp 服务器" ,  TFTPD32_TFTP_SERVER,	   TRUE,
	ONGLET_TFTP_CLIENT,   "Tftp 客户端",   TFTPD32_TFTP_CLIENT,   FALSE,
	ONGLET_DHCP_SERVER,   "DHCP 服务器",   TFTPD32_DHCP_SERVER,    TRUE,
	ONGLET_SYSLOG_SERVER, "系统日志服务器", TFTPD32_SYSLOG_SERVER,  TRUE,
	ONGLET_SNTP_SERVER,   "SNTP 服务器",   TFTPD32_SNTP_SERVER,    TRUE,
	ONGLET_DNS_SERVER,    "DNS 服务器",    TFTPD32_DNS_SERVER,    TRUE,
	ONGLET_EVENTS_VIEWER, "日志查看器",    TFTPD32_ALL_SERVICES,  FALSE,
};  // tTabCtrlData
// Ordonated list of the Client Controls 
static const int tTftpClientCtrl [] = 
{ 
    IDC_CLIENT_HOST, IDC_CLIENT_PORT, IDC_CLIENT_LOCALFILE, IDC_CLIENT_REMOTEFILE,
    IDC_CLIENT_GET_BUTTON, IDC_CLIENT_SEND_BUTTON
};     

    // Create tabs and add them label
    // code is really not optimized, but it is working
    // and since it is called only once...
    TabCtrlItem.mask = TCIF_TEXT | TCIF_PARAM   ;
    
	for ( nOnglet = 0;  nOnglet < SizeOfTab (tTabCtrlData) ; nOnglet++ )
	{
		// for local tabs (tftp client & event viewer use the settings)
		// for remote services use the report sent by the console
		// and saved into sGuiSettings.uRunningServices
        if (   tTabCtrlData[nOnglet].mask 
			& (tTabCtrlData[nOnglet].service ? sGuiSettings.uRunningServices : sGuiSettings.uServices) )
		{
			TabCtrlItem.pszText = tTabCtrlData[nOnglet].name;
			TabCtrlItem.lParam  = tTabCtrlData[nOnglet].tab ;
            TabCtrl_InsertItem(hTabWnd, nOnglet, (LPARAM) &  TabCtrlItem);
		}	// tab should be displayed
	} // all tabs


    TR_ResizeWindow(hDlgWnd, TRUE);
    // First available tab is selected
    TabCtrl_SetCurSel (hTabWnd, 0);
    TR_ChangeTabControl (hDlgWnd);

	// Place Tab ctrl at bottom of Z-order and all client control at top
	// Local File control will then accept drag an drop
    // (set also the other windows just to ease navigation with TAB)
	SetWindowPos (hTabWnd, HWND_BOTTOM, 0,0,0,0, SWP_NOMOVE|SWP_NOSIZE);
    for ( Ark=SizeOfTab (tTftpClientCtrl) ; Ark>0 ; Ark-- )
	    SetWindowPos ( GetDlgItem (hDlgWnd, tTftpClientCtrl [Ark-1]), 
		               HWND_TOP, 0,0,0,0, SWP_NOMOVE|SWP_NOSIZE );
return TRUE;
} // InitTabControl
Ejemplo n.º 16
0
int API4U SmtpSendMessage (LPCSTR szFrom, 
                           LPCSTR szTo, 
                           LPCSTR szMessage,
                           LPCSTR szHost, 
                           LPCSTR szLocalDomain)
{
int      Rc;
SOCKET   CSock=INVALID_SOCKET;
unsigned short usPort = SMTP4U_DEFPORT;
char     szBuf[2048];   /* overflow is not handled */


#define XX_RETURN(x) { \
    TcpClose (& CSock);  \
    Tcp4uLog (LOG4U_HIPROC, "exit SmtpSendMessage"); \
    return (x); }

   Tcp4uLog (LOG4U_HIPROC, "SmtpSendMessage");

   /* Ok search for SMTP server */
   Rc = TcpConnect(& CSock, szHost, "smtp", & usPort);
   if (Rc!=TCP4U_SUCCESS)  XX_RETURN (SMTP4U_CANTCONNECT);

   /* waits for incoming frame */
   Rc = TnProtoExchange (CSock,     /* used socket */
                         NULL,      /* no frame to be sent */
                         szBuf, sizeof szBuf, 
                         TnReadMultiLine, /* recv function */
                         SmtpProto[_SMTP4U_CONNECT].tAnswer, 
                         SizeOfTab(SmtpProto[_SMTP4U_CONNECT].tAnswer),
                         TRUE,      /* sensitive compare */
                         SMTP4U_DEFTIMEOUT, 
                         HFILE_ERROR);
   if (Rc != SMTP4U_SUCCESS)  
            XX_RETURN (Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc);

   /* sends the hello command */
   Sprintf (szBuf, 
            SmtpProto[_SMTP4U_HELO].szCmd, 
            szLocalDomain==NULL ? "" : szLocalDomain);
   Rc = TnProtoExchange (CSock,     /* used socket */
                         szBuf,      /* no frame to be sent */
                         szBuf, sizeof szBuf, 
                         TnReadMultiLine, /* recv function */
                         SmtpProto[_SMTP4U_HELO].tAnswer, 
                         SizeOfTab(SmtpProto[_SMTP4U_HELO].tAnswer),
                         TRUE,      /* sensitive compare */
                         SMTP4U_DEFTIMEOUT, 
                         HFILE_ERROR);
   if (Rc != SMTP4U_SUCCESS)  XX_RETURN (Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc);

   /* sends the Mail From */
   Sprintf (szBuf, SmtpProto[_SMTP4U_MAILFROM].szCmd, szFrom);
   Rc = TnProtoExchange (CSock,     /* used socket */
                         szBuf,      /* no frame to be sent */
                         szBuf, sizeof szBuf, 
                         TnReadMultiLine, /* recv function */
                         SmtpProto[_SMTP4U_MAILFROM].tAnswer, 
                         SizeOfTab(SmtpProto[_SMTP4U_MAILFROM].tAnswer),
                         TRUE,      /* sensitive compare */
                         SMTP4U_DEFTIMEOUT, 
                         HFILE_ERROR);
   if (Rc != SMTP4U_SUCCESS)  XX_RETURN (Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc);

   /* Rcpt command is handled by the SmtpSendRcpt function*/
   Rc = SmtpSendRcpt (CSock, szTo, szBuf, sizeof szBuf);
   if (Rc!=SMTP4U_SUCCESS)  XX_RETURN (Rc);
    
   /* sends the Data command */
   Rc = TnProtoExchange (CSock,     /* used socket */
                         SmtpProto[_SMTP4U_DATA].szCmd,
                         szBuf, sizeof szBuf, 
                         TnReadMultiLine, /* recv function */
                         SmtpProto[_SMTP4U_DATA].tAnswer, 
                         SizeOfTab(SmtpProto[_SMTP4U_DATA].tAnswer),
                         TRUE,      /* sensitive compare */
                         SMTP4U_DEFTIMEOUT, 
                         HFILE_ERROR);
   if (Rc != SMTP4U_SUCCESS)  XX_RETURN (Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc);

   /* Sends the data using TnSendMultiLine */
   TnSendMultiLine (CSock, SMTP4U_STDHEADER, TRUE, HFILE_ERROR);
   Rc = TnSendMultiLine (CSock, szMessage, TRUE, HFILE_ERROR);
   if (Rc<TN_SUCCESS)  XX_RETURN (SMTP4U_DATAERROR);

   /* sends the End of Data command */
   Rc = TnProtoExchange (CSock,     /* used socket */
                         SmtpProto[_SMTP4U_ENDOFDATA].szCmd,
                         szBuf, sizeof szBuf, 
                         TnReadMultiLine, /* recv function */
                         SmtpProto[_SMTP4U_ENDOFDATA].tAnswer, 
                         SizeOfTab(SmtpProto[_SMTP4U_ENDOFDATA].tAnswer),
                         TRUE,      /* sensitive compare */
                         SMTP4U_DEFTIMEOUT, 
                         HFILE_ERROR);
   if (Rc != SMTP4U_SUCCESS)  XX_RETURN (Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc);

   /* and Quit properly */
   Rc = TnProtoExchange (CSock,     /* used socket */
                         SmtpProto[_SMTP4U_QUIT].szCmd,
                         szBuf, sizeof szBuf, 
                         TnReadMultiLine, /* recv function */
                         SmtpProto[_SMTP4U_QUIT].tAnswer, 
                         SizeOfTab(SmtpProto[_SMTP4U_QUIT].tAnswer),
                         TRUE,      /* sensitive compare */
                         SMTP4U_DEFTIMEOUT, 
                         HFILE_ERROR);
XX_RETURN (Rc<TN_SUCCESS ? SMTP4U_DATAERROR : Rc);
#undef XX_RETURN
} /* SmtpSendMessage */
Ejemplo n.º 17
0
int ProcessDHCPMessage (struct dhcp_packet *pDhcpPkt, int *pSize)
{
unsigned char *p=NULL;
struct LL_IP  *pCurIP=NULL, *pProposedIP=NULL;	// Thanks Sam Leitch !
int            Ark, nDhcpType = 0;
struct in_addr sRequestedAddr;
DWORD sStaticIP;

    if (IsDHCP (*pDhcpPkt))
    {
       // search DHCP message type
       p = DHCPSearchOptionsField (pDhcpPkt->options, DHO_DHCP_MESSAGE_TYPE, NULL);
       if (p!=NULL)        nDhcpType = *p;
     }
    if (pDhcpPkt->yiaddr.s_addr!=INADDR_ANY  &&  pDhcpPkt->yiaddr.s_addr!=INADDR_NONE )
            return FALSE ; // address already assigned

     // the tab has one undef raw
     for (Ark=0 ; Ark<SizeOfTab(tDHCPType)-1 && nDhcpType!=tDHCPType[Ark].nType ; Ark++) ;
     LOG (5, "Rcvd %s Msg for IP %s, Mac %s",
                      tDHCPType[Ark].sType,
                      inet_ntoa (pDhcpPkt->ciaddr),
                      haddrtoa(pDhcpPkt->chaddr, pDhcpPkt->hlen,':'));


    // if (sParamDHCP.nPoolSize==0) return FALSE;   // no allocation pool --> listen only

     switch (nDhcpType)
     {
        case 0           :    // BootP
            if(sParamDHCP.nIgnoreBootp)
            {
               LOG (5, "Ignoring Bootp request");
               break;
            }
        case DHCPDISCOVER :
            sStaticIP = DHCP_StaticAssignation (pDhcpPkt);
			if (sStaticIP != INADDR_NONE)
			{
               LOG (0, "%s: statically assigned to address %s", 
								haddrtoa(pDhcpPkt->chaddr, pDhcpPkt->hlen,':'), 
								inet_ntoa (* (struct in_addr *) & sStaticIP) );
               pDhcpPkt->yiaddr.s_addr = sStaticIP;
			}
			else
			{
               p  = DHCPSearchOptionsField (pDhcpPkt->options, DHO_DHCP_REQUESTED_ADDRESS, NULL);
               if (p!=NULL)
              {
                   pDhcpPkt->ciaddr = * (struct in_addr *) p;
                   LOG (5, "Client requested address %s", inet_ntoa (pDhcpPkt->ciaddr));
              }
              pProposedIP  = DHCP_IPAllocate (nDhcpType, & pDhcpPkt->ciaddr, pDhcpPkt->chaddr, pDhcpPkt->hlen);
              if (pProposedIP == NULL)
              {
                  LOG (1, "no more address or address previously allocated by another server");
                  return FALSE;
              }
              pDhcpPkt->yiaddr.s_addr = pProposedIP->dwIP.s_addr;
              LOG (2, "%s: proposed address %s", IsDHCP(*pDhcpPkt) ? "DHCP" : "BOOTP", inet_ntoa (pProposedIP->dwIP) );

              //If this is a bootp, there is no other response from the client.  
              //Since we don't want leases expiring (or being mistaken for unAcked DHCP offers),
              //set renewed to a distant time
              if(nDhcpType == 0  &&  sStaticIP == INADDR_NONE)     // patched by Rolf Offermanns
                  ForceRenewTime(pProposedIP, 0x66666666);         // fixed by Sam Leitch
            } // dynamically assigned address

            // populate the packet to be returned
            pDhcpPkt->op = BOOTREPLY;
            // translate $IP$ and $MAC$ from boot file name
            TranslateExp (sParamDHCP.szBootFile, pDhcpPkt->file, pDhcpPkt->yiaddr, pDhcpPkt->chaddr);
           *pSize = DHCPOptionsReply (pDhcpPkt, DHCPOFFER);
            break ;

		//NJW Changed how requests are handled to mimic linux -- requests are responded to even if we didn't originally allocate, but only if the requested address is in our pool range

        case DHCPREQUEST :
         {BOOL bSERVER = FALSE;  // TRUE if Tftpd32 has assigned this address
           // Static Allocation ?
             // search field REQUEST ADDR in options
            sStaticIP = DHCP_StaticAssignation (pDhcpPkt);
			if (sStaticIP != INADDR_NONE)
			{
			    // populate the packet to be returned
                   pDhcpPkt->op = BOOTREPLY;
                   pDhcpPkt->yiaddr.s_addr = sStaticIP;
                 // translate $IP$ and $MAC$ from boot file name
                 TranslateExp (sParamDHCP.szBootFile, pDhcpPkt->file, pDhcpPkt->yiaddr, pDhcpPkt->chaddr);
                   *pSize = DHCPOptionsReply (pDhcpPkt, DHCPACK);
				   break;
			}

           // has tftpd32 dinamically assigned this address
           pCurIP = DHCPSearchByMacAddress (pDhcpPkt->chaddr, pDhcpPkt->hlen);
           if (pCurIP==NULL)  return FALSE; // not attributed by Tftpd32 --> do not answer
           // search field REQUEST ADDR in options
            // if specified should fit database
			p  = DHCPSearchOptionsField (pDhcpPkt->options, DHO_DHCP_REQUESTED_ADDRESS, NULL);
            if (p!=NULL)
			{
				pDhcpPkt->ciaddr = * (struct in_addr *) p;
			}

			if(AddrFitsPool(&pDhcpPkt->ciaddr))
			{
				//Look up the address, if it's not found, or the owner is this macaddr,
				//or the lease was expired, allow the serving.
				BOOL wasexpired = FALSE;
				pProposedIP = DHCPSearchByIP(&pDhcpPkt->ciaddr, &wasexpired);
				bSERVER = !pProposedIP || wasexpired || (0 == memcmp(pProposedIP->sMacAddr, pDhcpPkt->chaddr, 6));
			}

			if (bSERVER)
			{

				pProposedIP  = DHCP_IPAllocate (nDhcpType, & pDhcpPkt->ciaddr, pDhcpPkt->chaddr, pDhcpPkt->hlen);
				if (pProposedIP == NULL)
				{
					  LOG (1, "no more addresses or address previously allocated by another server");
					  return FALSE;
				}
				if (pProposedIP->tAllocated==0) SetAllocTime(pProposedIP);
				SetRenewTime(pProposedIP);
				LOG (5, "Previously allocated address %s acked", inet_ntoa (pProposedIP->dwIP));
				// populate the packet to be returned
				pDhcpPkt->op = BOOTREPLY;
				pDhcpPkt->yiaddr.s_addr = pProposedIP->dwIP.s_addr;
                TranslateExp (sParamDHCP.szBootFile, pDhcpPkt->file, pDhcpPkt->yiaddr, pDhcpPkt->chaddr);
				*pSize = DHCPOptionsReply (pDhcpPkt, DHCPACK);
			}
			else
			{
				LOG (5, "Client requested address %s which was not allocated by tftpd32 and is either outside our pool or is used by someone else",
							  inet_ntoa (pDhcpPkt->ciaddr) );
				return FALSE ; // do not answer
 			}
           } // Block for bSERVER declaration
           break;


        case DHCPDECLINE :
             // search current item and its precedent
          pCurIP = DHCPSearchByMacAddress (pDhcpPkt->chaddr, pDhcpPkt->hlen);
           if (pCurIP!=NULL)
           {
             p  = DHCPSearchOptionsField (pDhcpPkt->options, DHO_DHCP_REQUESTED_ADDRESS, NULL);
             if (p!=NULL) 
              {
                 sRequestedAddr.s_addr = * (DWORD *) p;
                 if ( pCurIP->dwIP.s_addr==sRequestedAddr.s_addr) 
                 {
                     DHCPDestroyItem (pCurIP);
                     LOG (5, "item destroyed");
                 }
             }
           }
		   //The decline is sent when an address is already in use.  Do an ARP and 
		   //add a lease for the in-use address
		   {
			 ULONG mac[2];
			 ULONG maclen = 6;
			// search field REQUEST ADDR in options
			// if specified should fit database
			p  = DHCPSearchOptionsField (pDhcpPkt->options, DHO_DHCP_REQUESTED_ADDRESS, NULL);
			if (p!=NULL)
			{
				pDhcpPkt->ciaddr = * (struct in_addr *) p;
			}

			 if(NO_ERROR == SendARP(pDhcpPkt->ciaddr.s_addr, 0, mac, &maclen))
			 {
				pProposedIP  = DHCP_IPAllocate (nDhcpType, & pDhcpPkt->ciaddr, (unsigned char*)mac, maclen);
				if (pProposedIP)
				{
					if (pProposedIP->tAllocated==0) SetAllocTime(pProposedIP);
					ForceRenewTime(pProposedIP, 0x66666666);   //Give a bootp lease, since the device may not do dhcp      
					LOG (5, "Added lease for existing address %s", inet_ntoa (pProposedIP->dwIP));
				}
			 }
		   }
           break;

        case DHCPRELEASE :
            // do not destroy the item but mark it free
           pCurIP = DHCPSearchByMacAddress (pDhcpPkt->chaddr, pDhcpPkt->hlen);
           if (pCurIP!=NULL) // then mac address found in table
           {
                ZeroAllocTime(pCurIP);
                ZeroRenewTime(pCurIP);
                LOG (5, "item %s released", haddrtoa(pDhcpPkt->chaddr, pDhcpPkt->hlen,':') );
           }
           break;
       } // switch type


DHCPScan();

// answer only to BootP, Request or discover msg
return  (nDhcpType==0 || nDhcpType==DHCPDISCOVER || nDhcpType==DHCPREQUEST);
} // ProcessDHCPMessage