메뉴 건너뛰기


Developer > Application


출처: http://blog.naver.com/x86ddk?Redirect=Log&logNo=80007509080


#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <windows.h>
#include <winnetwk.h>
/************************************************************************
 *                                                                      *
 *                               Macro                                  *
 *                                                                      *
 ************************************************************************/
#pragma comment( linker, "/INCREMENTAL:NO"    )
#pragma comment( linker, "/subsystem:console" )
#pragma comment( lib,    "kernel32.lib"       )
#pragma comment( lib,    "mpr.lib"            )
#pragma comment( lib,    "advapi32.lib"       )
#define VERSION             "1.10"
/************************************************************************
 *                                                                      *
 *                            Function Prototype                        *
 *                                                                      *
 ************************************************************************/
static void enumservice        ( char *target );
static void PrintWin32ErrorCUI ( char *message, DWORD dwMessageId );
static BOOL SessionBegin
(
    char *username,
    char *password,
    char *resource
);
static BOOL SessionEnd         ( char *resource );
static void usage              ( char *arg );
/************************************************************************
 *                                                                      *
 *                            Static Global Var                         *
 *                                                                      *
 ************************************************************************/
/************************************************************************/
static void enumservice ( char *target )
{
    SC_HANDLE               sc_handle           = ( SC_HANDLE )NULL;
    DWORD                   BytesNeeded         = 0,
                            ServicesReturned    = 0,
                            ResumeHandle        = 0,
                            error               = ERROR_SUCCESS,
                            count,
                            ServiceTypeIndex,
                            CurrentStateIndex;
    LPENUM_SERVICE_STATUS   enum_service_status = ( LPENUM_SERVICE_STATUS )NULL,
                            p                   = ( LPENUM_SERVICE_STATUS )NULL;
    char *         ServiceType[]       =
    {
        "",//
        "",//
        "",//
        "",//
        "",//
        "",//
        ""//
    };
    char *         CurrentState[]      =
    {
        "",//
        "",//
        "",//
        "",//
        "",//
        "",//
        "",//
        ""//
    };
    sc_handle   = OpenSCManager
                  (
                      target,
                      SERVICES_ACTIVE_DATABASE,
                      SC_MANAGER_ENUMERATE_SERVICE | GENERIC_READ
                  );
    if ( NULL == sc_handle )
    {
        PrintWin32ErrorCUI( "OpenSCManager() failed", GetLastError() );
        goto enumservice_exit;
    }
    if ( FALSE == EnumServicesStatus
                  (
                      sc_handle,
                      SERVICE_TYPE_ALL,
                      SERVICE_STATE_ALL,
                      NULL,
                      0,
                      &BytesNeeded,
                      &ServicesReturned,
                      &ResumeHandle
                  ) )
    {
        error = GetLastError();
        if ( ERROR_MORE_DATA != error )
        {
            PrintWin32ErrorCUI( "EnumServicesStatus() failed [0]", error );
            goto enumservice_exit;
        }
    }
    enum_service_status = ( LPENUM_SERVICE_STATUS )HeapAlloc
                          (
                              GetProcessHeap(),
                              HEAP_ZERO_MEMORY,
                              BytesNeeded
                          );
    if ( NULL == enum_service_status )
    {
        PrintWin32ErrorCUI( "HeapAlloc() failed [1]", ERROR_NOT_ENOUGH_MEMORY );
        goto enumservice_exit;
    }
    if ( FALSE == EnumServicesStatus
                  (
                      sc_handle,
                      SERVICE_TYPE_ALL,
                      SERVICE_STATE_ALL,
                      enum_service_status,
                      BytesNeeded,
                      &BytesNeeded,
                      &ServicesReturned,
                      &ResumeHandle
                  ) )
    {
        PrintWin32ErrorCUI( "EnumServicesStatus() failed [1]", GetLastError() );
        goto enumservice_exit;
    }
    p   = enum_service_status;
    for ( count = 0; count < ServicesReturned; count++, p++ )
    {
        if ( p->ServiceStatus.dwServiceType & SERVICE_KERNEL_DRIVER )
        {
            ServiceTypeIndex    = 0;
        }
        else if ( p->ServiceStatus.dwServiceType & SERVICE_FILE_SYSTEM_DRIVER )
        {
            ServiceTypeIndex    = 1;
        }
        else if ( p->ServiceStatus.dwServiceType & SERVICE_WIN32_OWN_PROCESS )
        {
            ServiceTypeIndex    = 2;
            if ( p->ServiceStatus.dwServiceType & SERVICE_INTERACTIVE_PROCESS )
            {
                ServiceTypeIndex    = 4;
            }
        }
        else if ( p->ServiceStatus.dwServiceType & SERVICE_WIN32_SHARE_PROCESS )
        {
            ServiceTypeIndex    = 3;
            if ( p->ServiceStatus.dwServiceType & SERVICE_INTERACTIVE_PROCESS )
            {
                ServiceTypeIndex    = 5;
            }
        }
        else
        {
            ServiceTypeIndex    = 6;
        }
        switch ( p->ServiceStatus.dwCurrentState )
        {
        case SERVICE_STOPPED:
            CurrentStateIndex   = 0;
            break;
        case SERVICE_START_PENDING:
            CurrentStateIndex   = 1;
            break;
        case SERVICE_STOP_PENDING:
            CurrentStateIndex   = 2;
            break;
        case SERVICE_RUNNING:
            CurrentStateIndex   = 3;
            break;
        case SERVICE_CONTINUE_PENDING:
            CurrentStateIndex   = 4;
            break;
        case SERVICE_PAUSE_PENDING:
            CurrentStateIndex   = 5;
            break;
        case SERVICE_PAUSED:
            CurrentStateIndex   = 6;
            break;
        default:
            CurrentStateIndex   = 7;
            break;
        }  /* end of switch */
        printf
        (
            "%-23s %-8s %-30s %s\n",
            ServiceType[ServiceTypeIndex],
            CurrentState[CurrentStateIndex],
            p->lpServiceName,
            p->lpDisplayName
        );
    }  /* end of for */
    printf
    (
        "ServicesReturned = %u\n",
        ServicesReturned
    );
enumservice_exit:
    if ( NULL != enum_service_status )
    {
        HeapFree( GetProcessHeap(), 0, enum_service_status );
        enum_service_status = ( LPENUM_SERVICE_STATUS )NULL;
    };
    if ( NULL != sc_handle )
    {
        CloseServiceHandle( sc_handle );
        sc_handle = ( SC_HANDLE )NULL;
    }
    return;
}  /* end of enumservice */
static void PrintWin32ErrorCUI ( char *message, DWORD dwMessageId )
{
    char *errMsg;
    FormatMessage
    (
        FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM,
        NULL,
        dwMessageId,
        MAKELANGID( LANG_NEUTRAL, SUBLANG_DEFAULT ),
        ( LPTSTR )&errMsg,
        0,
        NULL
    );
    fprintf( stderr, "%s: %s", message, errMsg );
    LocalFree( errMsg );
    return;
}  /* end of PrintWin32ErrorCUI */
static BOOL SessionBegin
(
    char *username,
    char *password,
    char *resource
)
{
    BOOL        ret = FALSE;
    DWORD       error;
    NETRESOURCE netresource;
    SessionEnd( resource );
    ZeroMemory( &netresource, sizeof( netresource ) );
    netresource.dwType       = RESOURCETYPE_ANY;
    netresource.lpLocalName  = NULL;
    netresource.lpRemoteName = resource;
    netresource.lpProvider   = NULL;
    error = WNetAddConnection2
            (
                &netresource,
                password,
                username,
                0
            );
    if ( NO_ERROR != error )
    {
        PrintWin32ErrorCUI( "WNetAddConnection2() failed", error );
        goto SessionBegin_exit;
    }
    ret = TRUE;
SessionBegin_exit:
    return( ret );
}  /* end of SessionBegin */
static BOOL SessionEnd ( char *resource )
{
    BOOL  ret = FALSE;
    DWORD error;
    error = WNetCancelConnection2
            (
                resource,
                CONNECT_UPDATE_PROFILE,
                TRUE
            );
    if ( NO_ERROR != error )
    {
        /*
         * PrintWin32ErrorCUI( "WNetCancelConnection2() failed", error );
         */
        goto SessionEnd_exit;
    }
    ret   = TRUE;
SessionEnd_exit:
    return( ret );
}  /* end of SessionEnd */
static void usage ( char *arg )
{
    fprintf
    (
        stderr,
        "Usage: %s [-h] [-v] [-t target] [-u username] [-p password]\n",
        arg
    );
    exit( EXIT_FAILURE );
}  /* end of usage */
int __cdecl main ( int argc, char * argv[] )
{
    int            c,
                   ret           = EXIT_FAILURE;
    char *target        = NULL,
                  *username      = NULL,
                  *password      = NULL,
                  *resource      = NULL;
    unsigned int   resourcelen   = 0;
    for ( c = 1; c < argc; c++ )
    {
        if ( ( ( argv[c][0] != '-' ) && ( argv[c][0] != '/' ) ) || ( strlen( argv[c] ) < 2 ) )
        {
            usage( argv[0] );
        }
        else
        {
            switch ( tolower( argv[c][1] ) )
            {
            case 't':
                if ( ( c + 1 ) >= argc )
                {
                    usage( argv[0] );
                }
                target      = argv[++c];
                break;
            case 'u':
                if ( ( c + 1 ) >= argc )
                {
                    usage( argv[0] );
                }
                username    = argv[++c];
                break;
            case 'p':
                if ( ( c + 1 ) >= argc )
                {
                    usage( argv[0] );
                }
                password    = argv[++c];
                break;
            case 'v':
                fprintf( stderr, "%s ver "VERSION"\n", argv[0] );
                return( EXIT_SUCCESS );
            case 'h':
            case '?':
            default:
                usage( argv[0] );
                break;
            }  /* end of switch */
        }
    }  /* end of for */
    if ( FALSE == SetConsoleCtrlHandler( NULL, FALSE ) )
    {
        PrintWin32ErrorCUI( "SetConsoleCtrlHandler() failed", GetLastError() );
        goto main_exit;
    }
    if ( NULL != target && NULL != username && NULL != password )
    {
        resourcelen = 2 + strlen( target ) + 1 + 4 + 1;
        resource    = (char*)HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, resourcelen );
        if ( NULL == resource )
        {
            PrintWin32ErrorCUI( "HeapAlloc() failed", ERROR_NOT_ENOUGH_MEMORY );
            goto main_exit;
        }
        sprintf( resource, "\\\\%s\\IPC$", target );
        SessionBegin( username, password, resource );
    }
    else
    {
        printf( "\n[Assuming one session already existed or target is null.]\n\n" );
    }
    enumservice( target );
    ret = EXIT_SUCCESS;
main_exit:
    if ( NULL != resource )
    {
        SessionEnd( resource );
        HeapFree( GetProcessHeap(), 0, resource );
        resource = NULL;
    }
    return( ret );
}



[출처] Enumerate Services|작성자 질럿