|
reSIProcate/repro
9694
|
00001 #if defined(HAVE_CONFIG_H) 00002 #include "config.h" 00003 #endif 00004 00005 #include "resip/stack/SipMessage.hxx" 00006 #include "resip/stack/Helper.hxx" 00007 #include "repro/monkeys/AmIResponsible.hxx" 00008 #include "repro/monkeys/IsTrustedNode.hxx" 00009 #include "repro/RequestContext.hxx" 00010 #include "repro/Proxy.hxx" 00011 #include <ostream> 00012 00013 #include "rutil/Logger.hxx" 00014 #define RESIPROCATE_SUBSYSTEM resip::Subsystem::REPRO 00015 00016 using namespace resip; 00017 using namespace repro; 00018 using namespace std; 00019 00020 AmIResponsible::AmIResponsible() : 00021 Processor("AmIResponsible") 00022 {} 00023 00024 AmIResponsible::~AmIResponsible() 00025 {} 00026 00027 Processor::processor_action_t 00028 AmIResponsible::process(RequestContext& context) 00029 { 00030 DebugLog(<< "Monkey handling request: " << *this 00031 << "; reqcontext = " << context); 00032 00033 resip::SipMessage& request = context.getOriginalRequest(); 00034 00035 // There should be no Routes on the request at this point, if there was a route, then 00036 // the StrictRouteFixup monkey would have routed to it already 00037 assert (!request.exists(h_Routes) || 00038 request.header(h_Routes).empty()); 00039 00040 // Topmost route had a flow-token; this is our problem 00041 if(!context.getTopRoute().uri().user().empty()) 00042 { 00043 resip::Tuple dest(Tuple::makeTupleFromBinaryToken(context.getTopRoute().uri().user().base64decode(), Proxy::FlowTokenSalt)); 00044 if(!(dest==resip::Tuple())) 00045 { 00046 // .bwc. Valid flow token 00047 std::auto_ptr<Target> target(new Target(request.header(h_RequestLine).uri())); 00048 target->rec().mReceivedFrom = dest; 00049 target->rec().mUseFlowRouting = true; 00050 context.getResponseContext().addTarget(target); 00051 return SkipThisChain; 00052 } 00053 } 00054 00055 // this if is just to be safe 00056 if (!request.exists(h_Routes) || 00057 request.header(h_Routes).empty()) 00058 { 00059 // !RjS! - Jason - check the RURI to see if the domain is 00060 // something this request is responsible for. If yes, then 00061 // just return Continue. If no make this call below. 00062 const Uri& uri = request.header(h_RequestLine).uri(); 00063 if (!context.getProxy().isMyUri(uri)) 00064 { 00065 // if this is not for a domain for which the proxy is responsible, 00066 // check that this sender is in our domain and send to the Request URI 00067 00068 // Ensure To header is well formed 00069 if(!request.header(h_To).isWellFormed()) 00070 { 00071 resip::SipMessage response; 00072 InfoLog(<<"Garbage in To header: needed for relay check."); 00073 Helper::makeResponse(response,context.getOriginalRequest(), 400, "Malformed To: header"); 00074 context.sendResponse(response); 00075 return Processor::SkipThisChain; 00076 } 00077 00078 // only perform relay check for out-of-dialog requests 00079 // !bwc! Um, then all anyone has to do to get us to be their relay 00080 // is throw in a spurious to-tag... 00081 // This smells funny. I am commenting it out. 00082 // .slg. Putting the ood check back in and clarifying the funny smell... 00083 // We only want to do this check for out of dialog requests, since 00084 // mid-dialog requests could be 403'd otherwise. Consider 00085 // an INVITE request from a repro domain user to a user in 00086 // another domain. The resulting ACK/200, BYE or any other 00087 // mid-dialog request coming from the remote domain, will contain 00088 // the repro users contact address in the RequestUri and a 00089 // foreign domain in the from header. We want to ensure these 00090 // requests are not 403'd. Byron's comment about an endpoint getting 00091 // us to relay by placing a spurious to tag in the request still 00092 // stands. Perhaps we ought to be checking the To header domain in 00093 // this case - however that is also weak, since the To header is not 00094 // used in routing and can easily be set to a URI in our domain to 00095 // trick repro into forwarding. Note: From header domain checking is 00096 // stronger than To header domain checking, since if the domain is 00097 // ours, then it must pass Digest Authentication (at least for non 00098 // ACK and BYE requests). 00099 // .bwc. I think that the only real way to solve the 00100 // I-don't-want-to-be-used-as-a-relay problem is crypto; specifically 00101 // Record-Route with crypto that states "Yeah, I set up this dialog, 00102 // let it through". 00103 if (!request.header(h_To).exists(p_tag)) 00104 { 00105 // Ensure From header is well formed 00106 if(!request.header(h_From).isWellFormed()) 00107 { 00108 resip::SipMessage response; 00109 InfoLog(<<"Garbage in From header: needed for relay check."); 00110 Helper::makeResponse(response,context.getOriginalRequest(), 400, "Malformed From: header"); 00111 context.sendResponse(response); 00112 return Processor::SkipThisChain; 00113 } 00114 00115 // !rwm! verify the AuthenticatioInfo object here. 00116 00117 // !rwm! TODO check some kind of relay list here 00118 // for now, just see if the sender claims to be from one of our domains 00119 // send a 403 if not on the list 00120 00121 // .slg. Allow trusted nodes to relay 00122 if (!context.getKeyValueStore().getBoolValue(IsTrustedNode::mFromTrustedNodeKey) && 00123 !context.getProxy().isMyUri(request.header(h_From).uri())) 00124 { 00125 // make 403, send, dispose of memory 00126 resip::SipMessage response; 00127 InfoLog (<< *this << ": will not relay to " << uri << " from " 00128 << request.header(h_From).uri() << ", send 403"); 00129 Helper::makeResponse(response, context.getOriginalRequest(), 403, "Relaying Forbidden"); 00130 context.sendResponse(response); 00131 return Processor::SkipThisChain; 00132 } 00133 } 00134 00135 std::auto_ptr<Target> target(new Target(request.header(h_RequestLine).uri())); 00136 context.getResponseContext().addTarget(target); 00137 00138 InfoLog (<< "Sending to requri: " << request.header(h_RequestLine).uri()); 00139 // skip the rest of the monkeys 00140 return Processor::SkipThisChain; 00141 } 00142 } 00143 return Processor::Continue; 00144 } 00145 00146 00147 /* ==================================================================== 00148 * The Vovida Software License, Version 1.0 00149 * 00150 * Copyright (c) 2000 Vovida Networks, Inc. All rights reserved. 00151 * 00152 * Redistribution and use in source and binary forms, with or without 00153 * modification, are permitted provided that the following conditions 00154 * are met: 00155 * 00156 * 1. Redistributions of source code must retain the above copyright 00157 * notice, this list of conditions and the following disclaimer. 00158 * 00159 * 2. Redistributions in binary form must reproduce the above copyright 00160 * notice, this list of conditions and the following disclaimer in 00161 * the documentation and/or other materials provided with the 00162 * distribution. 00163 * 00164 * 3. The names "VOCAL", "Vovida Open Communication Application Library", 00165 * and "Vovida Open Communication Application Library (VOCAL)" must 00166 * not be used to endorse or promote products derived from this 00167 * software without prior written permission. For written 00168 * permission, please contact vocal@vovida.org. 00169 * 00170 * 4. Products derived from this software may not be called "VOCAL", nor 00171 * may "VOCAL" appear in their name, without prior written 00172 * permission of Vovida Networks, Inc. 00173 * 00174 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED 00175 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 00176 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND 00177 * NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT SHALL VOVIDA 00178 * NETWORKS, INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT DAMAGES 00179 * IN EXCESS OF $1,000, NOR FOR ANY INDIRECT, INCIDENTAL, SPECIAL, 00180 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00181 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00182 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 00183 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00184 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE 00185 * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH 00186 * DAMAGE. 00187 * 00188 * ==================================================================== 00189 * 00190 * This software consists of voluntary contributions made by Vovida 00191 * Networks, Inc. and many individuals on behalf of Vovida Networks, 00192 * Inc. For more information on Vovida Networks, Inc., please see 00193 * <http://www.vovida.org/>. 00194 * 00195 */
1.7.5.1