|
SUMO - Simulation of Urban MObility
|
00001 /****************************************************************************/ 00007 // APIs for getting/setting lane values via TraCI 00008 /****************************************************************************/ 00009 // SUMO, Simulation of Urban MObility; see http://sumo.sourceforge.net/ 00010 // Copyright (C) 2001-2011 DLR (http://www.dlr.de/) and contributors 00011 /****************************************************************************/ 00012 // 00013 // This program is free software; you can redistribute it and/or modify 00014 // it under the terms of the GNU General Public License as published by 00015 // the Free Software Foundation; either version 2 of the License, or 00016 // (at your option) any later version. 00017 // 00018 /****************************************************************************/ 00019 00020 00021 // =========================================================================== 00022 // included modules 00023 // =========================================================================== 00024 #ifdef _MSC_VER 00025 #include <windows_config.h> 00026 #else 00027 #include <config.h> 00028 #endif 00029 00030 #include "TraCIConstants.h" 00031 #include <microsim/MSLane.h> 00032 #include "TraCIServerAPI_Lane.h" 00033 00034 #ifdef CHECK_MEMORY_LEAKS 00035 #include <foreign/nvwa/debug_new.h> 00036 #endif // CHECK_MEMORY_LEAKS 00037 00038 00039 // =========================================================================== 00040 // used namespaces 00041 // =========================================================================== 00042 using namespace traci; 00043 00044 00045 // =========================================================================== 00046 // method definitions 00047 // =========================================================================== 00048 bool 00049 TraCIServerAPI_Lane::processGet(TraCIServer& server, tcpip::Storage& inputStorage, 00050 tcpip::Storage& outputStorage) { 00051 std::string warning = ""; // additional description for response 00052 // variable 00053 int variable = inputStorage.readUnsignedByte(); 00054 std::string id = inputStorage.readString(); 00055 // check variable 00056 if (variable!=ID_LIST&&variable!=LANE_LINK_NUMBER&&variable!=LANE_EDGE_ID&&variable!=VAR_LENGTH 00057 &&variable!=VAR_MAXSPEED&&variable!=LANE_LINKS&&variable!=VAR_SHAPE 00058 &&variable!=VAR_CO2EMISSION&&variable!=VAR_COEMISSION&&variable!=VAR_HCEMISSION&&variable!=VAR_PMXEMISSION 00059 &&variable!=VAR_NOXEMISSION&&variable!=VAR_FUELCONSUMPTION&&variable!=VAR_NOISEEMISSION 00060 &&variable!=LAST_STEP_MEAN_SPEED&&variable!=LAST_STEP_VEHICLE_NUMBER 00061 &&variable!=LAST_STEP_VEHICLE_ID_LIST&&variable!=LAST_STEP_OCCUPANCY&&variable!=LAST_STEP_VEHICLE_HALTING_NUMBER 00062 &&variable!=LAST_STEP_LENGTH&&variable!=VAR_CURRENT_TRAVELTIME 00063 &&variable!=LANE_ALLOWED&&variable!=LANE_DISALLOWED&&variable!=VAR_WIDTH&&variable!=ID_COUNT) { 00064 server.writeStatusCmd(CMD_GET_LANE_VARIABLE, RTYPE_ERR, "Get Lane Variable: unsupported variable specified", outputStorage); 00065 return false; 00066 } 00067 // begin response building 00068 tcpip::Storage tempMsg; 00069 // response-code, variableID, objectID 00070 tempMsg.writeUnsignedByte(RESPONSE_GET_LANE_VARIABLE); 00071 tempMsg.writeUnsignedByte(variable); 00072 tempMsg.writeString(id); 00073 if (variable==ID_LIST) { 00074 std::vector<std::string> ids; 00075 MSLane::insertIDs(ids); 00076 tempMsg.writeUnsignedByte(TYPE_STRINGLIST); 00077 tempMsg.writeStringList(ids); 00078 } else if (variable==ID_COUNT) { 00079 std::vector<std::string> ids; 00080 MSLane::insertIDs(ids); 00081 tempMsg.writeUnsignedByte(TYPE_INTEGER); 00082 tempMsg.writeInt((int) ids.size()); 00083 } else { 00084 MSLane* lane = MSLane::dictionary(id); 00085 if (lane==0) { 00086 server.writeStatusCmd(CMD_GET_LANE_VARIABLE, RTYPE_ERR, "Lane '" + id + "' is not known", outputStorage); 00087 return false; 00088 } 00089 switch (variable) { 00090 case LANE_LINK_NUMBER: 00091 tempMsg.writeUnsignedByte(TYPE_UBYTE); 00092 tempMsg.writeUnsignedByte((int) lane->getLinkCont().size()); 00093 break; 00094 case LANE_EDGE_ID: 00095 tempMsg.writeUnsignedByte(TYPE_STRING); 00096 tempMsg.writeString(lane->getEdge().getID()); 00097 break; 00098 case VAR_LENGTH: 00099 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00100 tempMsg.writeDouble(lane->getLength()); 00101 break; 00102 case VAR_MAXSPEED: 00103 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00104 tempMsg.writeDouble(lane->getMaxSpeed()); 00105 break; 00106 case LANE_LINKS: { 00107 tempMsg.writeUnsignedByte(TYPE_COMPOUND); 00108 tcpip::Storage tempContent; 00109 unsigned int cnt = 0; 00110 tempContent.writeUnsignedByte(TYPE_INTEGER); 00111 const MSLinkCont& links = lane->getLinkCont(); 00112 tempContent.writeInt((int) links.size()); 00113 ++cnt; 00114 for (MSLinkCont::const_iterator i=links.begin(); i!=links.end(); ++i) { 00115 MSLink* link = (*i); 00116 // approached non-internal lane (if any) 00117 tempContent.writeUnsignedByte(TYPE_STRING); 00118 tempContent.writeString(link->getLane()!=0 ? link->getLane()->getID() : ""); 00119 ++cnt; 00120 // approached "via", internal lane (if any) 00121 tempContent.writeUnsignedByte(TYPE_STRING); 00122 #ifdef HAVE_INTERNAL_LANES 00123 tempContent.writeString(link->getViaLane()!=0 ? link->getViaLane()->getID() : ""); 00124 #else 00125 tempContent.writeString(""); 00126 #endif 00127 ++cnt; 00128 // priority 00129 tempContent.writeUnsignedByte(TYPE_UBYTE); 00130 tempContent.writeUnsignedByte(link->havePriority() ? 1 : 0); 00131 ++cnt; 00132 // opened 00133 tempContent.writeUnsignedByte(TYPE_UBYTE); 00134 tempContent.writeUnsignedByte(link->opened(MSNet::getInstance()->getCurrentTimeStep(), MSNet::getInstance()->getCurrentTimeStep(), 0.) ? 1 : 0); 00135 ++cnt; 00136 // approaching foe 00137 tempContent.writeUnsignedByte(TYPE_UBYTE); 00138 tempContent.writeUnsignedByte(link->hasApproachingFoe(MSNet::getInstance()->getCurrentTimeStep(), MSNet::getInstance()->getCurrentTimeStep()) ? 1 : 0); 00139 ++cnt; 00140 // state (not implemented, yet) 00141 tempContent.writeUnsignedByte(TYPE_STRING); 00142 tempContent.writeString(""); 00143 ++cnt; 00144 // direction (not implemented, yet) 00145 tempContent.writeUnsignedByte(TYPE_STRING); 00146 tempContent.writeString(""); 00147 ++cnt; 00148 // length 00149 tempContent.writeUnsignedByte(TYPE_DOUBLE); 00150 tempContent.writeDouble(link->getLength()); 00151 ++cnt; 00152 } 00153 tempMsg.writeInt((int) cnt); 00154 tempMsg.writeStorage(tempContent); 00155 } 00156 break; 00157 case LANE_ALLOWED: { 00158 const SUMOVehicleClasses& allowed = lane->getAllowedClasses(); 00159 std::vector<std::string> allowedS; 00160 for (SUMOVehicleClasses::const_iterator i=allowed.begin(); i!=allowed.end(); ++i) { 00161 allowedS.push_back(toString(*i)); 00162 } 00163 tempMsg.writeUnsignedByte(TYPE_STRINGLIST); 00164 tempMsg.writeStringList(allowedS); 00165 } 00166 case LANE_DISALLOWED: { 00167 const SUMOVehicleClasses& disallowed = lane->getNotAllowedClasses(); 00168 std::vector<std::string> disallowedS; 00169 for (SUMOVehicleClasses::const_iterator i=disallowed.begin(); i!=disallowed.end(); ++i) { 00170 disallowedS.push_back(toString(*i)); 00171 } 00172 tempMsg.writeUnsignedByte(TYPE_STRINGLIST); 00173 tempMsg.writeStringList(disallowedS); 00174 } 00175 break; 00176 case VAR_SHAPE: 00177 tempMsg.writeUnsignedByte(TYPE_POLYGON); 00178 tempMsg.writeUnsignedByte((int)MIN2(static_cast<size_t>(255),lane->getShape().size())); 00179 for (unsigned int iPoint=0; iPoint < MIN2(static_cast<size_t>(255),lane->getShape().size()); ++iPoint) { 00180 tempMsg.writeDouble(lane->getShape()[iPoint].x()); 00181 tempMsg.writeDouble(lane->getShape()[iPoint].y()); 00182 } 00183 break; 00184 case VAR_CO2EMISSION: 00185 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00186 tempMsg.writeDouble(lane->getHBEFA_CO2Emissions()); 00187 break; 00188 case VAR_COEMISSION: 00189 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00190 tempMsg.writeDouble(lane->getHBEFA_COEmissions()); 00191 break; 00192 case VAR_HCEMISSION: 00193 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00194 tempMsg.writeDouble(lane->getHBEFA_HCEmissions()); 00195 break; 00196 case VAR_PMXEMISSION: 00197 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00198 tempMsg.writeDouble(lane->getHBEFA_PMxEmissions()); 00199 break; 00200 case VAR_NOXEMISSION: 00201 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00202 tempMsg.writeDouble(lane->getHBEFA_NOxEmissions()); 00203 break; 00204 case VAR_FUELCONSUMPTION: 00205 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00206 tempMsg.writeDouble(lane->getHBEFA_FuelConsumption()); 00207 break; 00208 case VAR_NOISEEMISSION: 00209 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00210 tempMsg.writeDouble(lane->getHarmonoise_NoiseEmissions()); 00211 break; 00212 case LAST_STEP_VEHICLE_NUMBER: 00213 tempMsg.writeUnsignedByte(TYPE_INTEGER); 00214 tempMsg.writeInt((int) lane->getVehicleNumber()); 00215 break; 00216 case LAST_STEP_MEAN_SPEED: 00217 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00218 tempMsg.writeDouble(lane->getMeanSpeed()); 00219 break; 00220 case LAST_STEP_VEHICLE_ID_LIST: { 00221 std::vector<std::string> vehIDs; 00222 const std::deque<MSVehicle*> &vehs = lane->getVehiclesSecure(); 00223 for (std::deque<MSVehicle*>::const_iterator j=vehs.begin(); j!=vehs.end(); ++j) { 00224 vehIDs.push_back((*j)->getID()); 00225 } 00226 lane->releaseVehicles(); 00227 tempMsg.writeUnsignedByte(TYPE_STRINGLIST); 00228 tempMsg.writeStringList(vehIDs); 00229 } 00230 break; 00231 case LAST_STEP_OCCUPANCY: 00232 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00233 tempMsg.writeDouble(lane->getOccupancy()); 00234 break; 00235 case LAST_STEP_VEHICLE_HALTING_NUMBER: { 00236 int halting = 0; 00237 const std::deque<MSVehicle*> &vehs = lane->getVehiclesSecure(); 00238 for (std::deque<MSVehicle*>::const_iterator j=vehs.begin(); j!=vehs.end(); ++j) { 00239 if ((*j)->getSpeed()<0.1) { 00240 ++halting; 00241 } 00242 } 00243 lane->releaseVehicles(); 00244 tempMsg.writeUnsignedByte(TYPE_INTEGER); 00245 tempMsg.writeInt(halting); 00246 } 00247 break; 00248 case LAST_STEP_LENGTH: { 00249 SUMOReal lengthSum = 0; 00250 const std::deque<MSVehicle*> &vehs = lane->getVehiclesSecure(); 00251 for (std::deque<MSVehicle*>::const_iterator j=vehs.begin(); j!=vehs.end(); ++j) { 00252 lengthSum += (*j)->getVehicleType().getLengthWithGap(); 00253 } 00254 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00255 if (vehs.size()==0) { 00256 tempMsg.writeDouble(0); 00257 } else { 00258 tempMsg.writeDouble(lengthSum / (SUMOReal) vehs.size()); 00259 } 00260 lane->releaseVehicles(); 00261 } 00262 break; 00263 case VAR_CURRENT_TRAVELTIME: { 00264 SUMOReal meanSpeed = lane->getMeanSpeed(); 00265 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00266 if (meanSpeed!=0) { 00267 tempMsg.writeDouble(lane->getLength() / meanSpeed); 00268 } else { 00269 tempMsg.writeDouble(1000000.); 00270 } 00271 } 00272 break; 00273 case VAR_WIDTH: 00274 tempMsg.writeUnsignedByte(TYPE_DOUBLE); 00275 tempMsg.writeDouble(lane->getWidth()); 00276 break; 00277 default: 00278 break; 00279 } 00280 } 00281 server.writeStatusCmd(CMD_GET_LANE_VARIABLE, RTYPE_OK, warning, outputStorage); 00282 server.writeResponseWithLength(outputStorage, tempMsg); 00283 return true; 00284 } 00285 00286 00287 bool 00288 TraCIServerAPI_Lane::processSet(TraCIServer& server, tcpip::Storage& inputStorage, 00289 tcpip::Storage& outputStorage) { 00290 std::string warning = ""; // additional description for response 00291 // variable 00292 int variable = inputStorage.readUnsignedByte(); 00293 if (variable!=VAR_MAXSPEED&&variable!=VAR_LENGTH&&variable!=LANE_ALLOWED&&variable!=LANE_DISALLOWED) { 00294 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_ERR, "Change Lane State: unsupported variable specified", outputStorage); 00295 return false; 00296 } 00297 // id 00298 std::string id = inputStorage.readString(); 00299 MSLane* l = MSLane::dictionary(id); 00300 if (l==0) { 00301 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_ERR, "Lane '" + id + "' is not known", outputStorage); 00302 return false; 00303 } 00304 // process 00305 int valueDataType = inputStorage.readUnsignedByte(); 00306 switch (variable) { 00307 case VAR_MAXSPEED: { 00308 // speed 00309 if (valueDataType!=TYPE_DOUBLE) { 00310 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_ERR, "The speed must be given as a double.", outputStorage); 00311 return false; 00312 } 00313 SUMOReal val = inputStorage.readDouble(); 00314 l->setMaxSpeed(val); 00315 } 00316 break; 00317 case VAR_LENGTH: { 00318 // speed 00319 if (valueDataType!=TYPE_DOUBLE) { 00320 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_ERR, "The length must be given as a double.", outputStorage); 00321 return false; 00322 } 00323 SUMOReal val = inputStorage.readDouble(); 00324 l->setLength(val); 00325 } 00326 break; 00327 case LANE_ALLOWED: { 00328 if (valueDataType!=TYPE_STRINGLIST) { 00329 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_ERR, "Allowed classes must be given as a list of strings.", outputStorage); 00330 return false; 00331 } 00332 SUMOVehicleClasses allowed; 00333 parseVehicleClasses(inputStorage.readStringList(), allowed); 00334 l->setAllowedClasses(allowed); 00335 l->getEdge().rebuildAllowedLanes(); 00336 } 00337 break; 00338 case LANE_DISALLOWED: { 00339 if (valueDataType!=TYPE_STRINGLIST) { 00340 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_ERR, "Not allowed classes must be given as a list of strings.", outputStorage); 00341 return false; 00342 } 00343 SUMOVehicleClasses disallowed; 00344 parseVehicleClasses(inputStorage.readStringList(), disallowed); 00345 l->setNotAllowedClasses(disallowed); 00346 l->getEdge().rebuildAllowedLanes(); 00347 } 00348 break; 00349 default: 00350 break; 00351 } 00352 server.writeStatusCmd(CMD_SET_LANE_VARIABLE, RTYPE_OK, warning, outputStorage); 00353 return true; 00354 } 00355 00356 00357 /****************************************************************************/ 00358