CharSet VValueBag::DebugDump(char* inTextBuffer, sLONG& inBufferSize) const { if (VProcess::Get() != NULL) { VString dump; VString temp; VIndex i; VIndex count = GetAttributesCount(); for (i = 1 ; i <= count ; ++i) { const VValueSingle* theValue = GetNthAttribute( i, &temp); dump.AppendPrintf("%S = %A\n", &temp, theValue); } count = GetElementNamesCount(); for (i = 1 ; i <= count ; ++i) { const VBagArray *theBagArray = GetNthElementName( i, &temp); dump.AppendPrintf("=======\n%d %S :\n", theBagArray->GetCount(), &temp); for (sLONG j = 1 ; j <= theBagArray->GetCount() ; ++j) { dump.AppendPrintf("--\n%V", theBagArray->RetainNth(j)); } } dump.Truncate(inBufferSize/2); inBufferSize = (sLONG) dump.ToBlock(inTextBuffer, inBufferSize, VTC_UTF_16, false, false); } else inBufferSize = 0; return VTC_UTF_16; }
VError NameBuffer::Init(const VString& inName) { VSize n=inName.ToBlock(fName, sizeof(fName), VTC_UTF_8, false, false); //without trailing 0, no lenght prefix if(n==sizeof(fName)) return VE_INVALID_PARAMETER; //UTF8 name is more than NAME_MAX bytes long ; we do not support that. fName[n]=0; return VE_OK; }
VError XBsdNetAddr::FromIpAndPort(sLONG inFamily, const VString& inIP, PortNumber inPort) { //Small bug (feature ?) an IP v6 string too long is truncated and may become correct. char src[INET6_ADDRSTRLEN]; //with trailing 0 VSize len=inIP.ToBlock(src, sizeof(src), VTC_US_ASCII, true /*WithTrailingZero*/, false /*inWithLengthPrefix*/); if(len<=0) return vThrowError(VE_INVALID_PARAMETER); sLONG res=0; switch(inFamily) { case AF_INET : { IP4 dst; res=inet_pton(AF_INET, src, &dst); if(res>0) return FromIP4AndPort(dst, inPort); break; } case AF_INET6 : { IP6 dst; res=inet_pton(AF_INET, src, &dst); if(res>0) return FromIP6AndPort(dst, inPort); break; } default : return vThrowError(VE_SOCK_UNEXPECTED_FAMILY); } if(res<0) //an error occured vThrowNativeCombo(VE_INVALID_PARAMETER, errno); //if(res==0) ... not parsable (according to family) return vThrowError(VE_INVALID_PARAMETER); }
VError PathBuffer::Init(const VString& inPath, Mode inMode) { PathBuffer tmpBuf; char* buf=NULL; //If we want the real path of the file, we perform the UTF8 conversion in a tmp buffer and then the realpath transform in 'this' if(inMode==withRealPath) buf=tmpBuf.fPath; else buf=fPath; VSize n=inPath.ToBlock(buf, sizeof(fPath), VTC_UTF_8, false /*without trailing 0*/, false /*no lenght prefix*/); if(n==sizeof(fPath)) return VE_INVALID_PARAMETER; //UTF8 path is more than PATH_MAX bytes long ; we do not support that. buf[n]=0; if(inMode==withRealPath) return tmpBuf.RealPath(this); return VE_OK; }
VError XBsdAddrDnsQuery::FillAddrList(const VString& inDnsName, PortNumber inPort, Protocol inProto) { //Prepare the parameters for getaddrinfo. char utf8DnsName[255]; //Max DNS name VSize n=inDnsName.ToBlock(utf8DnsName, sizeof(utf8DnsName), VTC_UTF_8, false /*without trailing 0*/, false /*no lenght prefix*/); if(n==sizeof(utf8DnsName)) { return vThrowError(VE_INVALID_PARAMETER); //UTF8 path is too long ; we do not support that. } utf8DnsName[n]=0; char port[sizeof("65535")]; //Highest tcp port. int err=snprintf(port, sizeof(port), "%ld", (long)inPort); if(err<0 || err>sizeof(port)) { return vThrowError(VE_INVALID_PARAMETER); } addrinfo hints={0}; if(ResolveToV4() && !ResolveToV6()) hints.ai_family=AF_INET; else if(ResolveToV6() && !ResolveToV4()) hints.ai_family=AF_INET6, hints.ai_flags|=AI_V4MAPPED|AI_ALL; else hints.ai_family=AF_UNSPEC, hints.ai_flags|=AI_ADDRCONFIG; if(inProto==UDP) hints.ai_socktype=SOCK_DGRAM, hints.ai_protocol=IPPROTO_UDP; else hints.ai_socktype=SOCK_STREAM, hints.ai_protocol=IPPROTO_TCP; #if __MAC_OS_X_VERSION_MAX_ALLOWED >= __MAC_10_6 hints.ai_flags=AI_NUMERICSERV; //Numeric service only. #endif addrinfo* infoHead=NULL; //head of addr list do err=getaddrinfo(utf8DnsName, (inPort!=kBAD_PORT ? port : NULL), &hints, &infoHead); while(err==EAI_SYSTEM && errno==EINTR); if (err!=0) { if(infoHead!=NULL) freeaddrinfo(infoHead); return vThrowNativeError(errno); } for(addrinfo* infoPtr=infoHead ; infoPtr!=NULL ; infoPtr=infoPtr->ai_next) { /* Pour mémoire, ce qu'on récurpère ici : struct addrinfo { int ai_flags; int ai_family; int ai_socktype; int ai_protocol; socklen_t ai_addrlen; char *ai_canonname; struct sockaddr *ai_addr; struct addrinfo *ai_next; }; sockaddr_in */ const XBsdNetAddr xaddr(infoPtr->ai_addr); //xbox_assert(infoPtr->ai_family==xaddr.GetPfFamily()); //xbox_assert(infoPtr->ai_socktype==SOCK_STREAM); //xbox_assert(infoPtr->ai_protocol==IPPROTO_TCP); fVAddrList->PushXNetAddr(xaddr); } //Info list is no longer needed freeaddrinfo(infoHead); return VE_OK; }