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

📄 notlstnr.cpp

📁 funambol windows mobile plugin source code, the source code is taken from the funambol site
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/*
 * Copyright (C) 2003-2007 Funambol, Inc
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY, TITLE, NONINFRINGEMENT or FITNESS FOR A PARTICULAR
 * PURPOSE.  See the GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
 * 02111-1307  USA
 */

/* notlstnr.cpp : Defines the entry point for the DLL application.
*                  Handle all the interaction with Services.exe and
*                  with the netwotk. Uses class S4JProxy to interact
*                  with sync4j engine.
*/

#include "stdafx.h"
#include "notlstnr.h"
#include "Notify.h"
#include <stdio.h>
#include <service.h>
#include <iptypes.h>
#include <winsock2.h>
#include <ws2tcpip.h>
#include <Pmpolicy.h>

#include "logutils.h"
#include "s4jproxy.h"
#include "worker.h"
#include "notify/checknet.h"
#include "notify/s4n_service.h"
#include "notify/addresschange.h"
#include "pim/SettingFunctions.h"
#include "base/startcmd.h"
#include "base/util/utils.h"
#include "processUtils.h"

#include "CTPConfig.h"
#include "CTPManager.h"
#include "CTPMessage.h"


#define LOGLEVEL 1


// Service state
static DWORD g_dwServiceState = SERVICE_STATE_UNINITIALIZED;
// Global critical section
static CRITICAL_SECTION g_cs;

//static
DWORD addressChangeHandler(void);
static DWORD acceptConnection(SOCKET sock);

int getPushTypeFromRegistry();


HANDLE moduleHandle = 0;

///////////////////////////////////////////////////////////////////
// Notification Listener: Dll entry
///////////////////////////////////////////////////////////////////
/**
* Dll entry point.
*/
extern "C" BOOL WINAPI DllMain(HANDLE hInstDll, DWORD fdwReason,
        LPVOID lpvReserved) {
    switch (fdwReason) {
        case DLL_PROCESS_ATTACH:
            g_dwServiceState = SERVICE_STATE_UNINITIALIZED;
            InitializeCriticalSection (&g_cs);
            // This DLL does not require thread attatch/deatch
            DisableThreadLibraryCalls((HMODULE)hInstDll);
            DebugInit(LOGLEVEL, true);
            DebugPrint(L"Process attach.");
            moduleHandle = hInstDll;
            break;

        case DLL_PROCESS_DETACH:
            DeleteCriticalSection (&g_cs);
            DebugPrint(L"Process detach.");
            DebugEnd();
            moduleHandle = 0;
            break;
    }
    return TRUE;
}


///////////////////////////////////////////////////////////////////
// Notification Listener: service callbaks
///////////////////////////////////////////////////////////////////
/**
* Service callback: not implemented.
*/
APIEXPORT BOOL S4N_Open(
        DWORD dwData,
        DWORD dwAccess,
        DWORD dwShareMode
        ) {
    DebugPrint(TEXT("Open - dwData: %lx, dwAccess: %lx, dwShareMode: %lx"),
          dwData, dwAccess, dwShareMode);

    return TRUE;
}

/**
* Service callback: not implemented.
*/
APIEXPORT BOOL S4N_Close( DWORD dwData) {
    DebugPrint(TEXT("Close - dwData: %lx\n"), dwData);
    return TRUE;
}

/**
* Service callback: close the socket and exit.
*/
APIEXPORT BOOL S4N_Deinit( DWORD dwData) {
    DebugPrint(TEXT("Deinit - dwData: %lx\n"), dwData);

    //MessageBox (NULL, TEXT("DeInit"), TEXT("Test"), MB_SETFOREGROUND | MB_OK);
    
    // Stop child threads of STP.
    stopWorker();

    // Stop CTP process: try to send the BYE message and 
    // then close the socket connection.
    CTPManager* ctpManager = CTPManager::getInstance();
    ctpManager->stopCTP();

    //stopCheckForNews();
    DebugEnd();
    // Remove unattended mode
    PowerPolicyNotify(PPN_UNATTENDEDMODE, FALSE);

    return TRUE;
}

/**
* Service callback: init the service and return the listen port.
*/
APIEXPORT DWORD S4N_Init( DWORD dwData) {
    EnterCriticalSection (&g_cs);
    if (g_dwServiceState != SERVICE_STATE_UNINITIALIZED) {
        // Someone is trying to load multiple times
        DebugPrint(L"S4ND: ERROR: service already initialized on S4N_Init() call\r\n");
        LeaveCriticalSection (&g_cs);
        return 0;
    }

    Log(0, "", "notlstnr.txt");
    LOG.setLevel(LOG_LEVEL_DEBUG);

    g_dwServiceState = SERVICE_STATE_STARTING_UP;
    DebugInit(LOGLEVEL);
    DebugPrint(L"S4ND: S4N_Init success - service is in starting up state\r\n");

    LeaveCriticalSection (&g_cs);
    return getListenerPort();
}

/**
* Service callback: main method containing the service.exe events.
* On IOCTL_SERVICE_REFRESH and IOCTL_SERVICE_NOTIFY_ADDR_CHANGE events, it is invoked
* a new ip address change notification to the server.
* On IOCTL_SERVICE_CONNECTION event it is opened a socket connection listening
* for the server messages
*/
APIEXPORT BOOL S4N_IOControl(
        DWORD dwData,
        DWORD dwCode,
        PBYTE pBufIn,
        DWORD dwLenIn,
        PBYTE pBufOut,
        DWORD dwLenOut,
        PDWORD pdwActualOut
        )
{
    DWORD dwError = ERROR_INVALID_PARAMETER;

    // DebugPrint(TEXT("IOControl - dwCode: %lx\n"), dwCode);

    EnterCriticalSection (&g_cs);

    switch(dwCode){
        // Control code sent to start a service.  (services start FIN0:)
        case IOCTL_SERVICE_START:
            if (g_dwServiceState != SERVICE_STATE_OFF) {
                DebugPrint(L"S4ND: ERROR: IOCTL_SERVICE_START"
                        L" fails because service is not off. "
                        L"State=<%d>\r\n",g_dwServiceState);
                dwError = ERROR_SERVICE_ALREADY_RUNNING;
            }
            else {
                // Notification listener must work in unattended mode
                PowerPolicyNotify(PPN_UNATTENDEDMODE, TRUE);

                DebugPrint(L"S4ND: State changed to ON\r\n");
                g_dwServiceState = SERVICE_STATE_ON;
                dwError = ERROR_SUCCESS;
            }
            break;

        // Control code sent to refresh a service. (services refresh FIN0:)
        case IOCTL_SERVICE_REFRESH:

            if (g_dwServiceState != SERVICE_STATE_ON) {
                DebugPrint(L"S4ND:ERROR:IOCTL_SERVICE_REFRESH"
                        L" fails because service is not on. "
                        L"State=<%d>\r\n",g_dwServiceState);
                dwError = ERROR_SERVICE_NOT_ACTIVE;
            }
            else {
                DebugPrint(L"S4ND: Stop on a refresh\r\n");
                g_dwServiceState = SERVICE_STATE_SHUTTING_DOWN;
                stopWorker();
                DebugEnd();
                // Wait for tasks to terminate
                Sleep(1000);
                // Shut the service down, re-read configuration
                // TODO: close connections? Abort sync?
                // (if we have any) and then restart.
                DebugPrint(L"S4ND: Restarting on refresh\r\n");
                g_dwServiceState = SERVICE_STATE_ON;
                dwError = ERROR_SUCCESS;
                addressChangeHandler();
            }
            break;

        // Control code sent to stop a service.  (services stop S4N0:)
        case IOCTL_SERVICE_STOP:
            // No longer accept new network connections.
            // Close existing connections
            if (g_dwServiceState != SERVICE_STATE_ON) {
                DebugPrint(L"S4ND:ERROR:IOCTL_SERVICE_STOP "
                        L"fails.  Service state is not on. "
                        L"Current State=<%d>\r\n",
                        g_dwServiceState);
                dwError = ERROR_SERVICE_NOT_ACTIVE;
            }
            else {
                DebugPrint(L"S4ND: Service stopping\r\n");
                stopWorker();
                DebugEnd();
                g_dwServiceState = SERVICE_STATE_OFF;
                dwError = ERROR_SUCCESS;
            }
            break;

        // An application (possibly services.exe itself) is
        // querying for the service's running state.
        case IOCTL_SERVICE_STATUS:
            // No need for critical section since this is an atomic read.
            __try {
                if (pBufOut && dwLenOut == sizeof(DWORD)) {
                    *(DWORD *)pBufOut = g_dwServiceState;
                    if (pdwActualOut)
                        *pdwActualOut = sizeof(DWORD);
                    dwError = ERROR_SUCCESS;
                }
            }
            __except (EXCEPTION_EXECUTE_HANDLER) {
                DebugPrint(L"S4ND: ERROR Invalid pointer "
                        L"on IOCTL_SERVICE_STATUS\r\n");
                dwError = ERROR_INVALID_PARAMETER;
            }
            break;
        // Services.exe has completed super-service init for this service.
        // Incoming super-service connections can come in at anytime now.
        case IOCTL_SERVICE_STARTED:
            if (g_dwServiceState != SERVICE_STATE_STARTING_UP) {
                DebugPrint(L"S4ND:ERROR:IOCTL_SERVICE_STARTED"
                        L" failed because state != starting up. "
                        L"State=<%d>\r\n",g_dwServiceState);
                dwError = ERROR_SERVICE_ALREADY_RUNNING;
            }
            else {
                DebugPrint(L"S4ND: IOCTL_SERVICE_STARTED "
                        L" changed state to SERVICE_STATE_ON\r\n");
                g_dwServiceState = SERVICE_STATE_ON;
                dwError = ERROR_SUCCESS;
            }
            addressChangeHandler();
            break;

        // IP address changed: notify the server
        case IOCTL_SERVICE_NOTIFY_ADDR_CHANGE:
            dwError = addressChangeHandler();
            break;

        // A new connection request
        case IOCTL_SERVICE_CONNECTION:
            if (dwLenIn != sizeof(SOCKET)) {
                dwError = ERROR_INVALID_PARAMETER;
            }
            else {
                SOCKET sock;

                __try {
                    sock = * ((SOCKET*)pBufIn);
                }
                __except (EXCEPTION_EXECUTE_HANDLER) {
                    dwError = ERROR_INVALID_PARAMETER;
                    break;
                }
                // Call new connection handler
                dwError = acceptConnection(sock);
            }
            break;
        default:
            //DebugPrint(TEXT("IOControl - dwCode: %lx\n"), dwCode);
            return TRUE;
    }

    if (dwError != ERROR_SUCCESS)
        SetLastError(dwError);

    LeaveCriticalSection(&g_cs);

    return (dwError==ERROR_SUCCESS);
}

/**
* Service callback: not implemented.
*/
APIEXPORT DWORD S4N_Read(
        DWORD dwData,
        LPVOID pBuf,
        DWORD dwLen
        ) {
    DebugPrint(TEXT("Read - dwData: %lx\n"), dwData);
    return 0;
}

/**
* Service callback: not implemented.
*/

⌨️ 快捷键说明

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