Merge "Removed original Hydrogen demo from repo."
[packetcable.git] / packetcable-driver / src / main / java / org / pcmm / PCMMPdpReqStateMan.java
1 /*
2  * (c) 2015 Cable Television Laboratories, Inc.  All rights reserved.
3  */
4
5 package org.pcmm;
6
7 import org.pcmm.gates.IGateID;
8 import org.pcmm.gates.IPCMMError.ErrorCode;
9 import org.pcmm.gates.IPCMMGate;
10 import org.pcmm.gates.ITransactionID;
11 import org.pcmm.gates.ITransactionID.GateCommandType;
12 import org.pcmm.gates.impl.PCMMError;
13 import org.pcmm.gates.impl.PCMMGateReq;
14 import org.slf4j.Logger;
15 import org.slf4j.LoggerFactory;
16 import org.umu.cops.prpdp.COPSPdpException;
17 import org.umu.cops.prpdp.COPSPdpReqStateMan;
18 import org.umu.cops.stack.*;
19 import org.umu.cops.stack.COPSReportType.ReportType;
20
21 import java.net.Socket;
22 import java.util.Arrays;
23 import java.util.HashMap;
24 import java.util.Map;
25
26 /**
27  * State manager class for provisioning requests, at the PDP side.
28  */
29 public class PCMMPdpReqStateMan extends COPSPdpReqStateMan {
30
31     private final static Logger logger = LoggerFactory.getLogger(PCMMPdpReqStateMan.class);
32
33     /**
34      * Object for performing policy data processing
35      */
36     protected final PCMMPdpDataProcess _thisProcess;
37
38     /** COPS message transceiver used to send COPS messages */
39     protected final PCMMPdpMsgSender _sender;
40
41     /**
42      * Creates a request state manager
43      * @param clientType    Client-type
44      * @param clientHandle  Client handle
45      */
46     // TODO - consider sending in the COPSHandle object instead
47     public PCMMPdpReqStateMan(final short clientType, final COPSHandle clientHandle, final PCMMPdpDataProcess process,
48                               final Socket socket) {
49         super(clientType, clientHandle, process, socket);
50         this._thisProcess = process;
51         _sender = new PCMMPdpMsgSender(_clientType, _handle, _socket);
52         // Initial state
53         _status = Status.ST_INIT;
54     }
55
56     @Override
57     public void processRequest(final COPSReqMsg msg) throws COPSPdpException {
58         // TODO - Implement me - see commented out code from history prior to May 4, 2015...
59     }
60
61      // TODO - break apart this method
62     @Override
63     protected void processReport(final COPSReportMsg msg) throws COPSPdpException {
64         // Report Type
65         final COPSReportType rtypemsg = msg.getReport();
66
67         if (msg.getClientSI() != null) {
68             final COPSClientSI clientSI = msg.getClientSI();
69             // Named ClientSI
70             final byte[] data = Arrays.copyOfRange(clientSI.getData().getData(), 0, clientSI.getData().getData().length);
71
72             // PCMMUtils.WriteBinaryDump("COPSReportClientSI", data);
73             logger.info("PCMMGateReq Parse Gate Message");
74             final PCMMGateReq gateMsg = PCMMGateReq.parse(data);
75
76             // TODO FIXME - Why is this Map being filled but never used???
77             final Map<String, String> repSIs = new HashMap<>();
78             String strobjprid = "";
79             final COPSPrObjBase obj = new COPSPrObjBase(clientSI.getData().getData());
80             switch (obj.getSNum()) {
81                 case COPSPrObjBase.PR_PRID:
82                     logger.info("COPSPrObjBase.PR_PRID");
83                     // TODO FIXME - this value is never used
84                     strobjprid = obj.getData().str();
85                     break;
86                 case COPSPrObjBase.PR_EPD:
87                     logger.info("COPSPrObjBase.PR_EPD");
88                     // TODO FIXME - strobjprid is always empty
89                     repSIs.put(strobjprid, obj.getData().str());
90                     logger.info("PRID: " + strobjprid);
91                     logger.info("EPD: " + obj.getData().str());
92                     break;
93                 default:
94                     logger.error("Object s-num: " + obj.getSNum() + "stype " + obj.getSType());
95                     logger.error("PRID: " + strobjprid);
96                     logger.error("EPD: " + obj.getData().str());
97                     break;
98             }
99
100             logger.info("rtypemsg process");
101             //** Here we must act in accordance with
102             //** the report received
103
104             // retrieve and remove the transactionId to gate request map entry
105             // see PCMMPdpMsgSender.sendGateSet(IPCMMGate gate)
106             final ITransactionID trID = gateMsg.getTransactionID();
107             final Short trIDnum = trID.getTransactionIdentifier();
108
109             logger.info("Removing gate from cache with key - " + trIDnum);
110             final IPCMMGate gate = PCMMGlobalConfig.transactionGateMap.remove(trIDnum);
111             if (gate != null) {
112                 // capture the "error" message if any
113                 gate.setError(gateMsg.getError());
114                 logger.info("Setting error on gate - " + gateMsg.getError());
115             }else {
116                 logger.error("processReport(): gateReq not found for transactionID {}", trIDnum);
117                 return;
118             }
119
120             if (rtypemsg.getReportType().equals(ReportType.SUCCESS)) {
121                 logger.info("rtypemsg success");
122                 _status = Status.ST_REPORT;
123                 final IGateID gateID = gateMsg.getGateID();
124                 logger.info("Setting gate ID on gate object - " + gateID);
125                 gate.setGateID(gateID);
126                 if (_thisProcess != null)
127                     _thisProcess.successReport(this, gateMsg);
128             } else {
129                 final String cmdType;
130                 if (trID.getGateCommandType().equals(GateCommandType.GATE_DELETE_ACK)) {
131                     cmdType = "GateDeleteAck";
132                 } else if (trID.getGateCommandType().equals(GateCommandType.GATE_SET_ACK)) {
133                     cmdType = "GateSetAck";
134                 } else cmdType = null;
135                 // capture the gateId from the response message
136                 final IGateID gateID = gateMsg.getGateID();
137                 logger.info("Setting gate ID on gate object - " + gateID);
138                 gate.setGateID(gateID);
139
140                 if (gateID != null) {
141                     int gateIdInt = gateID.getGateID();
142                     String gateIdHex = String.format("%08x", gateIdInt);
143                     logger.info(getClass().getName() + ": " + cmdType + ": GateID = " + gateIdHex);
144                 } else {
145                     logger.warn("Gate ID is null");
146                 }
147             }
148             if (rtypemsg.getReportType().equals(ReportType.FAILURE)) {
149                 logger.info("rtypemsg failure");
150                 _status = Status.ST_REPORT;
151                 if (_thisProcess != null)
152                     _thisProcess.failReport(this, gateMsg);
153                 else
154                     if (gateMsg.getError() != null)
155                         logger.info("Gate message error - " + gateMsg.getError().toString());
156                     else {
157                         // TODO - Determine if this is the correct error code
158                         final PCMMError error = new PCMMError(ErrorCode.UNK_GATE_CMD);
159                         gate.setError(error);
160                         logger.warn("Gate request failed without an error, setting one - " + error);
161                     }
162             } else if (rtypemsg.getReportType().equals(ReportType.ACCOUNTING)) {
163                     logger.info("rtypemsg account");
164                     _status = Status.ST_ACCT;
165                     if (_thisProcess != null)
166                         _thisProcess.acctReport(this, gateMsg);
167             }
168
169             // let the waiting gateSet/gateDelete sender proceed
170             // TODO - see PCMMService#processReport() gate.notify(). Should determine a better means to
171             // TODO - handle this synchronization.
172             logger.info("Notify gate request has been updated with ID - " + gate.getGateID());
173             synchronized(gate) {
174                 gate.notify();
175             }
176             logger.info("Out processReport");
177         }
178     }
179
180 }