Monday, March 28, 2011

Console Application to discover Effective Named Pipe Path of a WCF net.pipe Endpoint

As I have promised in my previous post, I am making available a C++ console application to troubleshoot named pipes endpoints in WCF. Below is a screenshot of the application:
Application logic:
  • It gets the endpoint from the command line and substitute the host name by +, * depending on the wildcard mode.
  • It then add a “/” to the end if not present already and transform to up case all characters of pipe and path
  • If the size of the resulting string is bigger than 128 characters a hash is applied to the resulting string  (not implemented)
  • The final name is net.pipe:E + Base64 of string generated in item 2 or net.pipe:H + Base64 of string generated in item 3 if uri is bigger than 128 characters
 Post detailing the problem:
Source Code is as shown below (subject to this license: http://rodneyviana.codeplex.com/license).
// ReadMemory.cpp : Defines the entry point for the console application. 
//
#include "stdafx.h"
void NormalizeEndPoint(const std::wstring &source, std::wstring& normal) 
    normal.assign(source);
    if(!normal.compare(0, 10, L"net.pipe://")) 
    { 
        normal.clear(); 
        return; 
    }
    int hoststart = normal.find_first_of(L"//"); 
    int hostend = normal.find(L"/", hoststart+2);
    std::wstring ending(normal.substr(hostend)); 
    std::wstring starting(normal.substr(0, hoststart).append(L"//+")); 
    std::transform(ending.begin(), ending.end(), ending.begin(), (int(*)(int))std::toupper); 
    std::wstring normalized(starting.append(ending)); 
    if(normalized.substr(normalized.length()-1).compare(L"/")) 
    { 
        normalized.append(L"/"); 
    } 
    
    normal.assign(normalized); 
    return;
}
void ShowSyntax(bool SyntaxError) 
    std::wprintf(L"ReadMemory version 1.0\n"); 
    std::wprintf(L"Written by Rodney Viana - http://blogs.msdn.com/rodneyviana\n"); 
    std::wprintf(L"\n"); 
    if(SyntaxError) 
        std::wprintf(L"Syntax Error\n\n");
    std::wprintf(L"Syntax:\n"); 
    std::wprintf(L"ReadMemory <PipeNameEndPoint> | -file <MappedMemoryFile>\n"); 
    std::wprintf(L"Where:\t<PipeNameEndPoint> is a endpoint for a net.pipe in WCF in\n\t the format net.pipe://host/path\n"); 
    std::wprintf(L"\t<MappedMemoryFile> is a memory mapped file\n"); 
    std::wprintf(L"\n"); 
    std::wprintf(L"Examples\n"); 
    std::wprintf(L"\tReadMemory net.pipe://localhost/Service/Service1\n");