📄 servhs.cpp
字号:
}else if (cmpCGIarg(cmd,"cmd=","connect")) { Servent *s = servMgr->servents; { char tmp[64]; sprintf(tmp,"c%d=",s->serventIndex); if (cmpCGIarg(cmd,tmp,"1")) { if (hasCGIarg(cmd,"stop")) s->thread.active = false; } s=s->next; } sprintf(jumpStr,"/%s/connections.html",servMgr->htmlPath);
jumpArg = jumpStr; }else if (cmpCGIarg(cmd,"cmd=","shutdown")) { servMgr->shutdownTimer = 1; }else if (cmpCGIarg(cmd,"cmd=","stop")) { GnuID id; char *cp = cmd; while (cp=nextCGIarg(cp,curr,arg)) { if (strcmp(curr,"id")==0) id.fromStr(arg); } Channel *c = chanMgr->findChannelByID(id); if (c) c->thread.active = false; sys->sleep(500); sprintf(jumpStr,"/%s/relays.html",servMgr->htmlPath);
jumpArg = jumpStr; }else if (cmpCGIarg(cmd,"cmd=","bump")) { GnuID id; char *cp = cmd; while (cp=nextCGIarg(cp,curr,arg)) { if (strcmp(curr,"id")==0) id.fromStr(arg); } Channel *c = chanMgr->findChannelByID(id); if (c) c->bump = true; sprintf(jumpStr,"/%s/relays.html",servMgr->htmlPath);
jumpArg = jumpStr; }else if (cmpCGIarg(cmd,"cmd=","keep")) { GnuID id; char *cp = cmd; while (cp=nextCGIarg(cp,curr,arg)) { if (strcmp(curr,"id")==0) id.fromStr(arg); } Channel *c = chanMgr->findChannelByID(id); if (c) c->stayConnected = true; sprintf(jumpStr,"/%s/relays.html",servMgr->htmlPath);
jumpArg = jumpStr; }else if (cmpCGIarg(cmd,"cmd=","relay")) {
ChanInfo info; char *cp = cmd; while (cp=nextCGIarg(cp,curr,arg)) { if (strcmp(curr,"id")==0) info.id.fromStr(arg); } if (!chanMgr->findChannelByID(info.id)) { ChanHitList *chl = chanMgr->findHitList(info); if (!chl) throw StreamException("channel not found"); Channel *c = chanMgr->createChannel(chl->info,NULL); if (!c) throw StreamException("out of channels"); c->stayConnected = true; c->startGet(); } sprintf(jumpStr,"/%s/relays.html",servMgr->htmlPath);
jumpArg = jumpStr; }else if (cmpCGIarg(cmd,"net=","add")) { GnuID id; id.clear(); while (cmd=nextCGIarg(cmd,curr,arg)) { if (strcmp(curr,"ip")==0) { Host h; h.fromStrIP(arg,DEFAULT_PORT); if (servMgr->addOutgoing(h,id,true)) LOG_NETWORK("Added connection: %s",arg); }else if (strcmp(curr,"id")==0) { id.fromStr(arg); } } }else if (cmpCGIarg(cmd,"cmd=","logout")) { jumpArg = "/"; servMgr->cookieList.remove(cookie); }else if (cmpCGIarg(cmd,"cmd=","login")) { GnuID id; char idstr[64]; id.generate(); id.toStr(idstr); cookie.set(idstr,sock->host.ip); servMgr->cookieList.add(cookie); http.writeLine(HTTP_SC_FOUND); if (servMgr->cookieList.neverExpire) http.writeLineF("%s id=%s; path=/; expires=\"Mon, 01-Jan-3000 00:00:00 GMT\";",HTTP_HS_SETCOOKIE,idstr); else http.writeLineF("%s id=%s; path=/;",HTTP_HS_SETCOOKIE,idstr); http.writeLineF("Location: /%s/index.html",servMgr->htmlPath); http.writeLine("");
}else{ sprintf(jumpStr,"/%s/index.html",servMgr->htmlPath);
jumpArg = jumpStr;
} } }catch(StreamException &e) { html.startTagEnd("h1","ERROR - %s",e.msg); LOG_ERROR("html: %s",e.msg); } if (retHTML) { if (jumpArg) { String jmp(jumpArg,String::T_HTML); jmp.convertTo(String::T_ASCII); html.locateTo(jmp.cstr()); } }}// -----------------------------------static XML::Node *createChannelXML(Channel *c){ XML::Node *n = c->info.createChannelXML(); n->add(c->createRelayXML(true)); n->add(c->info.createTrackXML());// n->add(c->info.createServentXML()); return n;}// -----------------------------------static XML::Node *createChannelXML(ChanHitList *chl){ XML::Node *n = chl->info.createChannelXML(); n->add(chl->createXML()); n->add(chl->info.createTrackXML());// n->add(chl->info.createServentXML()); return n;}// ----------------------------------- void Servent::handshakeXML(){ int i; XML xml; XML::Node *rn = new XML::Node("peercast"); xml.setRoot(rn); rn->add(new XML::Node("servent uptime=\"%d\"",servMgr->getUptime())); rn->add(new XML::Node("bandwidth out=\"%d\" in=\"%d\"",
stats.getPerSecond(Stats::BYTESOUT)-stats.getPerSecond(Stats::LOCALBYTESOUT),
stats.getPerSecond(Stats::BYTESIN)-stats.getPerSecond(Stats::LOCALBYTESIN)
));
rn->add(new XML::Node("connections total=\"%d\" relays=\"%d\" direct=\"%d\"",servMgr->totalConnected(),servMgr->numStreams(Servent::T_RELAY,true),servMgr->numStreams(Servent::T_DIRECT,true)));
XML::Node *an = new XML::Node("channels_relayed total=\"%d\"",chanMgr->numChannels());
rn->add(an);
Channel *c = chanMgr->channel;
while (c)
{
if (c->isActive())
an->add(createChannelXML(c));
c=c->next;
}
// add public channels { XML::Node *fn = new XML::Node("channels_found total=\"%d\"",chanMgr->numHitLists()); rn->add(fn);
ChanHitList *chl = chanMgr->hitlist; while (chl)
{ if (chl->isUsed())
fn->add(createChannelXML(chl));
chl = chl->next;
}
}
#if 0
if (servMgr->isRoot)
{
// add private channels
{
XML::Node *pn = new XML::Node("priv_channels");
rn->add(pn);
ChanHitList *chl = chanMgr->hitlist;
while (chl)
{
if (chl->isUsed())
if (chl->info.isPrivate())
pn->add(createChannelXML(chl));
chl = chl->next;
}
}
}
#endif
XML::Node *hc = new XML::Node("host_cache"); for(i=0; i<ServMgr::MAX_HOSTCACHE; i++) { ServHost *sh = &servMgr->hostCache[i]; if (sh->type != ServHost::T_NONE) { char ipstr[64]; sh->host.toStr(ipstr); hc->add(new XML::Node("host ip=\"%s\" type=\"%s\" time=\"%d\"",ipstr,ServHost::getTypeStr(sh->type),sh->time)); } }
rn->add(hc);
sock->writeLine(HTTP_SC_OK);
sock->writeLineF("%s %s",HTTP_HS_SERVER,PCX_AGENT);
sock->writeLineF("%s %s",HTTP_HS_CONTENT,MIME_XML);
sock->writeLine("Connection: close");
sock->writeLine("");
xml.write(*sock);
}// -----------------------------------void Servent::readICYHeader(HTTP &http, ChanInfo &info, char *pwd){ char *arg = http.getArgStr(); if (!arg) return; if (http.isHeader("x-audiocast-name") || http.isHeader("icy-name") || http.isHeader("ice-name"))
{ info.name.set(arg,String::T_ASCII);
info.name.convertTo(String::T_UNICODE);
}else if (http.isHeader("x-audiocast-url") || http.isHeader("icy-url") || http.isHeader("ice-url"))
info.url.set(arg,String::T_ASCII); else if (http.isHeader("x-audiocast-bitrate") || (http.isHeader("icy-br")) || http.isHeader("ice-bitrate") || http.isHeader("icy-bitrate")) info.bitrate = atoi(arg); else if (http.isHeader("x-audiocast-genre") || http.isHeader("ice-genre") || http.isHeader("icy-genre"))
{ info.genre.set(arg,String::T_ASCII);
info.genre.convertTo(String::T_UNICODE);
}else if (http.isHeader("x-audiocast-description") || http.isHeader("ice-description"))
{ info.desc.set(arg,String::T_ASCII);
info.desc.convertTo(String::T_UNICODE);
}else if (http.isHeader("Authorization")) http.getAuthUserPass(NULL,pwd); else if (http.isHeader(PCX_HS_CHANNELID)) info.id.fromStr(arg);
else if (http.isHeader("ice-password")) { if (pwd) if (strlen(arg) < 64) strcpy(pwd,arg); }else if (http.isHeader("content-type")) { if (stristr(arg,MIME_OGG)) info.contentType = ChanInfo::T_OGG; else if (stristr(arg,MIME_XOGG)) info.contentType = ChanInfo::T_OGG; else if (stristr(arg,MIME_MP3)) info.contentType = ChanInfo::T_MP3; else if (stristr(arg,MIME_XMP3)) info.contentType = ChanInfo::T_MP3; else if (stristr(arg,MIME_WMA)) info.contentType = ChanInfo::T_WMA; else if (stristr(arg,MIME_WMV)) info.contentType = ChanInfo::T_WMV; else if (stristr(arg,MIME_ASX)) info.contentType = ChanInfo::T_ASX; else if (stristr(arg,MIME_NSV)) info.contentType = ChanInfo::T_NSV; else if (stristr(arg,MIME_RAW)) info.contentType = ChanInfo::T_RAW;
else if (stristr(arg,MIME_MMS)) info.srcProtocol = ChanInfo::SP_MMS;
else if (stristr(arg,MIME_XPCP))
info.srcProtocol = ChanInfo::SP_PCP;
else if (stristr(arg,MIME_XPEERCAST))
info.srcProtocol = ChanInfo::SP_PEERCAST;
else if (stristr(arg,MIME_XSCPLS)) info.contentType = ChanInfo::T_PLS; else if (stristr(arg,MIME_PLS)) info.contentType = ChanInfo::T_PLS; else if (stristr(arg,MIME_XPLS)) info.contentType = ChanInfo::T_PLS; else if (stristr(arg,MIME_M3U)) info.contentType = ChanInfo::T_PLS; else if (stristr(arg,MIME_MPEGURL))
info.contentType = ChanInfo::T_PLS;
else if (stristr(arg,MIME_TEXT)) info.contentType = ChanInfo::T_PLS; }}// -----------------------------------void Servent::handshakeICY(Channel::SRC_TYPE type, bool isHTTP){ ChanInfo info; HTTP http(*sock); // default to mp3 for shoutcast DSP (doesn`t send content-type) if (type == Channel::SRC_SHOUTCAST) info.contentType = ChanInfo::T_MP3; while (http.nextHeader()) { LOG_DEBUG("ICY %s",http.cmdLine); readICYHeader(http,info,loginPassword); } // check password before anything else, if needed if (strcmp(servMgr->password,loginPassword)!=0)
{
if (!sock->host.isLocalhost() || strlen(loginPassword))
throw HTTPException(HTTP_SC_UNAUTHORIZED,401);
}
// we need a valid IP address before we start
servMgr->checkFirewall();
// attach channel ID to name, channel ID is also encoded with IP address // to help prevent channel hijacking. info.id = chanMgr->broadcastID;
info.id.encode(NULL,info.name.cstr(),loginMount,info.bitrate); LOG_DEBUG("Incoming source: %s : %s",info.name.cstr(),ChanInfo::getTypeStr(info.contentType)); if (isHTTP) sock->writeStringF("%s\n\n",HTTP_SC_OK); else sock->writeLine("OK");
Channel *c = chanMgr->findChannelByID(info.id); if (c)
{
LOG_CHANNEL("ICY channel already active, closing old one");
c->thread.shutdown();
}
info.comment = chanMgr->broadcastMsg; info.bcID = chanMgr->broadcastID;
c = chanMgr->createChannel(info,loginMount); if (!c) throw HTTPException(HTTP_SC_UNAVAILABLE,503);
c->startICY(sock,type);}
// -----------------------------------
void Servent::handshakeLocalFile(const char *fn)
{
HTTP http(*sock);
String fileName;
fileName = peercastApp->getPath();
fileName.append(fn);
LOG_DEBUG("Writing HTML file: %s",fileName.cstr());
HTML html("",*sock);
char *args = strstr(fileName.cstr(),"?");
if (args)
*args++=0;
if (fileName.contains(".htm"))
{
html.writeOK(MIME_HTML);
html.writeTemplate(fileName.cstr(),args);
}else if (fileName.contains(".css"))
{
html.writeOK(MIME_CSS);
html.writeRawFile(fileName.cstr());
}else if (fileName.contains(".jpg"))
{
html.writeOK(MIME_JPEG);
html.writeRawFile(fileName.cstr());
}else if (fileName.contains(".gif"))
{
html.writeOK(MIME_GIF);
html.writeRawFile(fileName.cstr());
}else if (fileName.contains(".png"))
{
html.writeOK(MIME_PNG);
html.writeRawFile(fileName.cstr());
}
}
// -----------------------------------
void Servent::handshakeRemoteFile(const char *dirName)
{
ClientSocket *rsock = sys->createSocket();
if (!rsock)
throw HTTPException(HTTP_SC_UNAVAILABLE,503);
const char *hostName = "www.peercast.org"; // hardwired for "security"
Host host;
host.fromStrName(hostName,80);
rsock->open(host);
rsock->connect();
HTTP rhttp(*rsock);
rhttp.writeLineF("GET /%s HTTP/1.0",dirName);
rhttp.writeLineF("%s %s",HTTP_HS_HOST,hostName);
rhttp.writeLineF("%s %s",HTTP_HS_CONNECTION,"close");
rhttp.writeLineF("%s %s",HTTP_HS_ACCEPT,"*/*");
rhttp.writeLine("");
String contentType;
bool isTemplate = false;
while (rhttp.nextHeader())
{
char *arg = rhttp.getArgStr();
if (arg)
{
if (rhttp.isHeader("content-type"))
contentType = arg;
}
}
MemoryStream mem(100*1024);
while (!rsock->eof())
{
int len=0;
char buf[4096];
len = rsock->readUpto(buf,sizeof(buf));
if (len==0)
break;
else
mem.write(buf,len);
}
rsock->close();
int fileLen = mem.getPosition();
mem.len = fileLen;
mem.rewind();
if (contentType.contains(MIME_HTML))
isTemplate = true;
sock->writeLine(HTTP_SC_OK);
sock->writeLineF("%s %s",HTTP_HS_SERVER,PCX_AGENT);
sock->writeLineF("%s %s",HTTP_HS_CACHE,"no-cache");
sock->writeLineF("%s %s",HTTP_HS_CONNECTION,"close");
sock->writeLineF("%s %s",HTTP_HS_CONTENT,contentType.cstr());
sock->writeLine("");
if (isTemplate)
{
HTML html("",*sock);
html.readTemplate(mem,sock,0);
}else
sock->write(mem.buf,fileLen);
mem.free();
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -