fxStr garbage;
bool gotresponse = false;
gotRTNC = false;
+ ctrlFrameRcvd = fxStr::null;
do {
c = getModemChar(60000);
if (c == DLE) {
break;
}
} else garbage.append(c);
+ if (gotCTRL && garbage.length() > 2 && (garbage[0] & 0xFF) == 0xFF &&
+ (garbage[garbage.length()-2] & 0xFF) == 0x10 &&
+ (garbage[garbage.length()-1] & 0xFF) == 0x03) {
+ // We got a control frame and won't get the channel change...
+ for (u_int i = 0; i < garbage.length()-2; i++) {
+ if ((garbage[i] & 0xFF) == DLE && ++i < garbage.length()) {
+ /*
+ * We've got a frame and must apply T.31-A1 Table B.1.
+ */
+ if ((garbage[i] & 0xFF) == 0x07) { // end of HDLC frame w/FCS error
+ // what to do? send CRP? discard frame?
+ continue;
+ }
+ switch (garbage[i] & 0xFF) {
+ case DLE: // <DLE><DLE> => <DLE>
+ ctrlFrameRcvd.append(DLE);
+ break;
+ case SUB: // <DLE><SUB> => <DLE><DLE>
+ ctrlFrameRcvd.append(DLE);
+ ctrlFrameRcvd.append(DLE);
+ break;
+ case 0x51: // <DLE><0x51> => <DC1>
+ ctrlFrameRcvd.append(DC1);
+ break;
+ case 0x53: // <DLE><0x53> => <DC3>
+ ctrlFrameRcvd.append(0x13);
+ break;
+ }
+ } else
+ ctrlFrameRcvd.append(garbage[i] & 0xFF);
+ }
+ return (false);
+ }
fxStr rcpsignal;
rcpsignal.append(0xFF); rcpsignal.append(0x03); rcpsignal.append(0x86); rcpsignal.append(0x69);
rcpsignal.append(0xCB); rcpsignal.append(0x10); rcpsignal.append(0x03);
bool gotRTNC; // retrain control channel
u_short primaryV34Rate; // rate indication for primary channel
u_short controlV34Rate; // rate indication for control channel
+ fxStr ctrlFrameRcvd; // unexpected control channel frame received
// modem setup stuff
virtual bool setupModem();
if (!gotEOT) {
bool gotprimary = waitForDCEChannel(false);
u_short rtnccnt = 0;
- while (!gotEOT && gotRTNC && rtnccnt++ < 3) {
+ while (!gotEOT && (gotRTNC || (ctrlFrameRcvd != fxStr::null)) && rtnccnt++ < 3) {
/*
- * Remote requested control channel retrain; the remote
+ * Remote requested control channel retrain and/or the remote
* didn't properly hear our last signal. So now we have to
- * wait for a signal from the remote and then respond appropriately
+ * use a signal from the remote and then respond appropriately
* to get us back in sync. DCS::CFR - PPS::PPR/MCF - EOR::ERR
*/
if (flowControl == FLOW_XONXOFF)
(void) setXONXOFF(FLOW_NONE, FLOW_NONE, ACT_DRAIN);
setInputBuffering(false);
HDLCFrame rtncframe(conf.class1FrameOverhead);
- if (recvFrame(rtncframe, conf.t2Timer)) {
+ bool gotrtncframe = false;
+ if (ctrlFrameRcvd != fxStr::null) {
+ gotrtncframe = true;
+ for (u_int i = 0; i < ctrlFrameRcvd.length(); i++)
+ rtncframe.put(frameRev[ctrlFrameRcvd[i] & 0xFF]);
+ traceHDLCFrame("-->", rtncframe);
+ } else
+ gotrtncframe = recvFrame(rtncframe, conf.t2Timer);
+ if (gotrtncframe) {
switch (rtncframe.getFCF()) {
case FCF_DCS:
// hopefully it didn't change on us!
}
}
break;
+ case FCF_DCN:
+ tracePPM("RECV recv", rtncframe.getFCF());
+ gotEOT = true;
+ continue;
+ break;
}
setInputBuffering(true);
if (flowControl == FLOW_XONXOFF)