function [response, objectID] = readSubscription(result)
%readSubscription Internal function to read the TraCI subscriptions.

%   Copyright 2013 Universidad Nacional de Colombia,
%   Politecnico Jaime Isaza Cadavid.
%   Authors: Andres Acosta, Jairo Espinosa, Jorge Espinosa.
%   $Id: readSubscription.m 17 2014-05-30 14:32:09Z afacostag $

import traci.constants
global edgeSubscriptionResults guiSubscriptionResults ...
    loopSubscriptionResults junctionSubscriptionResults ...
    laneSubscriptionResults detSubscriptionResults ...
    poiSubscriptionResults polygonSubscriptionResults ...
    routeSubscriptionResults simSubscriptionResults ...
    tlSubscriptionResults vehSubscriptionResults ...
    typeSubscriptionResults

subscriptionResults = containers.Map({...
    constants.RESPONSE_SUBSCRIBE_INDUCTIONLOOP_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_MULTI_ENTRY_EXIT_DETECTOR_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_TL_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_LANE_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_VEHICLE_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_VEHICLETYPE_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_ROUTE_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_POI_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_POLYGON_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_JUNCTION_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_EDGE_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_SIM_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_GUI_VARIABLE,...
    constants.RESPONSE_SUBSCRIBE_INDUCTIONLOOP_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_MULTI_ENTRY_EXIT_DETECTOR_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_TL_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_LANE_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_VEHICLE_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_VEHICLETYPE_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_ROUTE_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_POI_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_POLYGON_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_JUNCTION_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_EDGE_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_SIM_CONTEXT,...
    constants.RESPONSE_SUBSCRIBE_GUI_CONTEXT,...
    constants.CMD_GET_INDUCTIONLOOP_VARIABLE,...
    constants.CMD_GET_MULTI_ENTRY_EXIT_DETECTOR_VARIABLE,...
    constants.CMD_GET_TL_VARIABLE,...
    constants.CMD_GET_LANE_VARIABLE,...
    constants.CMD_GET_VEHICLE_VARIABLE,...
    constants.CMD_GET_VEHICLETYPE_VARIABLE,...
    constants.CMD_GET_ROUTE_VARIABLE,...
    constants.CMD_GET_POI_VARIABLE,...
    constants.CMD_GET_POLYGON_VARIABLE,...
    constants.CMD_GET_JUNCTION_VARIABLE,...
    constants.CMD_GET_EDGE_VARIABLE,...
    constants.CMD_GET_SIM_VARIABLE,...
    constants.CMD_GET_GUI_VARIABLE},...
    {loopSubscriptionResults, detSubscriptionResults,...
    tlSubscriptionResults, laneSubscriptionResults,...
    vehSubscriptionResults, typeSubscriptionResults,...
    routeSubscriptionResults, poiSubscriptionResults,...
    polygonSubscriptionResults, junctionSubscriptionResults,...
    edgeSubscriptionResults, simSubscriptionResults,...
    guiSubscriptionResults,...
    loopSubscriptionResults, detSubscriptionResults,...
    tlSubscriptionResults, laneSubscriptionResults,...
    vehSubscriptionResults, typeSubscriptionResults,...
    routeSubscriptionResults, poiSubscriptionResults,...
    polygonSubscriptionResults, junctionSubscriptionResults,...
    edgeSubscriptionResults, simSubscriptionResults,...
    guiSubscriptionResults,...
    loopSubscriptionResults, detSubscriptionResults,...
    tlSubscriptionResults, laneSubscriptionResults,...
    vehSubscriptionResults, typeSubscriptionResults,...
    routeSubscriptionResults, poiSubscriptionResults,...
    polygonSubscriptionResults, junctionSubscriptionResults,...
    edgeSubscriptionResults, simSubscriptionResults,...
    guiSubscriptionResults,...
    });
result.readLength();
response = result.read(1);
strresponse = ['0x' sprintf('%x',response)];
% Determine if the subscription is context related.
isVariableSubscription = response>=sscanf(...
    traci.constants.RESPONSE_SUBSCRIBE_INDUCTIONLOOP_VARIABLE,'%x')...
    && response<=sscanf(traci.constants.RESPONSE_SUBSCRIBE_GUI_VARIABLE,'%x');
objectID = result.readString();

% Read the domain if the subscription was made to a context
if ~isVariableSubscription
    domain = result.read(1);
    strdomain = ['0x' sprintf('%.2x',domain)];
end

% Read the number of variables to which the client is subscribed
numVars = result.read(1);

% Populate the global TraCI modules
if isVariableSubscription
    while numVars > 0
        varID = result.read(1);
		status = result.read(1);
		result.read(1);
        if status
			traci.close();
            throw(MException('traci:FatalTraciError','Error %s', result.readString()));
        elseif isKey(subscriptionResults, strresponse)
            subsResultsHandle = subscriptionResults(strresponse);
            subsResultsHandle.add(objectID,...
                ['0x' sprintf('%.2x',varID)], result);
        else
            throw(MException('traci:FatalTraciError','Cannot handle subscription response %s for %s\n',...
                num2str(response), objectID));
        end
        numVars = numVars - 1;
    end
else
    objectNo = result.readInt();
    for o=1:objectNo
        oid = result.readString();
        for v=1:numVars
            varID = result.read(1);
			status = result.read(1);
			result.read(1);
            if status
                throw(MException('traci:FatalTraciError','Error %s', result.readString()));
            elseif isKey(subscriptionResults, strresponse)
                subsResultsHandle = subscriptionResults(strresponse);
                domainHandle = subscriptionResults(strdomain);
                subsResultsHandle.addContext(objectID, domainHandle, oid, ['0x' sprintf('%.2x',varID)], result);
            else
                throw(MException('traci:FatalTraciError','Cannot handle subscription response %.2x for %s.', num2str(response), objectID));
            end
        end
    end
end