Tom: C++: Modem ansprechen - klappt nicht

Beitrag lesen

Hello,

Noch einer eine Idee?

Nur aus der Assembler- und Pascalzeit unter DOS.
Man musste das Modem-Steuerregister und das Modem-Statusregister gezielt ansprechen.

Hier ein Stück davon in Pascal-Code. Das Assemblerbeispiel finde ich gerade nicht.
Übrigens funktioniert dieses alte Programm, wozu das Stück gehört, immer noch in der Command-Box von WinXP.

Die C-Funktionen SetupComm() und SetCommState() sollten das aber eigentlich besorgen.

Wenn Du eine reine Windowslösung (ab 95b) haben willst, musst Du aber die Schnittstellen erst vom OS freigeben lassen, wenn Du sie selber ansprechen willst auf einer tieferen Ebene. Das habe ich leider vergessen, wie das ging. Aber solange Windows selber auf der COM-Schnittstelle sitzt, lässt es Dein Programm nicht ran.

procedure InstCom(ComNr:byte;Direct:Char);

var   BaudMSB    : byte;
      BaudLSB    : byte;
      LtgSteuReg : byte;
      LtgStatReg : byte;
      Zeichen    : byte;

begin
  IntMskReg:=Port[$21];
  Port[$21]:=(IntMskReg or $18);        { IRQ von COM1 und COM2 ausmaskieren }

case ComNr of
    1: begin
         ComBasis:=Com1Basis;
         GetIntVec($0C,OldIntComX);               { IVT 13 = IRQ 4 }
         SetIntVec($0C,Addr(Receive));
         Port[$21]:=(IntMskReg and $EF);          { IRQ von COM1 zulassen }
       end;
    2: begin
         ComBasis:=Com2Basis;
         GetIntVec($0B,OldIntComX);               { IVT 12 = IRQ3 }
         SetIntVec($0B,Addr(Receive));
         Port[$21]:=(IntMskReg and $F7);          { IRQ von COM2 zulassen }
       end;
    3: begin
         ComBasis:=Com3Basis;
         GetIntVec($0D,OldIntComX);               { IVT 14 = IRQ5 }
         SetIntVec($0D,Addr(Receive));
         Port[$21]:=(IntMskReg and $DF);          { IRQ von COM3 zulassen }
       end;
       { Um Intr-Anforderung zuzulassen, muá das Bit auf 0 stehen !!}
  end;

{-------Baudrate einstellen---------->  Baudrate = 1.8432MHz / (16*Teiler)
                                     ==>  Baudrate = 115200kHz / Teiler }
  BaudMSB := (115200 div Preset.Baud div 256);
  BaudLSB := (115200 div Preset.Baud);

Port[ComBasis+3]:=128;                { LtgSteuReg zum Einstellen der
                                          Baud-Rate vorbereiten }
  Port[ComBasis]:=BaudLSB;              { LSB des Teilers für Baudrate }
  Port[ComBasis+1]:=BaudMSB;            { MSB des Teilers für Baudrate }

{-------Leitungs-Steuerregister setzen -------------}
  LtgSteuReg := 0
    or (Preset.Bit-5)                   { Anzahl der šbertragungs-Bits}
    or ((Preset.Stop-1)*4);             { Anzahl der Stopbits setzen }

case Preset.Parity of
    'K': null;                          { keine Paritätsprüfung }
    'G': LtgSteuReg:=LtgSteuReg or 24;  { Gerade Parit„t einstellen }
    'U': LtgSteuReg:=LtgSteuReg or 8;   { Ungerade Parit„t einstellen }
  end;
  Port[ComBasis+3]:=LtgSteuReg;         { Leitungssteuerreg. setzen für
                                          Datenübertragung }

{-------Interrupt-Aktivierungs-Register setzen -----}
  if (Direct in ['E','D']) then
    Port[ComBasis+1]:=1                 { IntReq wenn Zeichen vorliegt }
  else
    Port[ComBasis+1]:=0;                { kein IntReq }

{-------definierte Startwerte herstellen -----------}
  LtgStatReg:=Port[ComBasis+5];         { LtgStatReg einmal auslesen }
  Zeichen:=Port[ComBasis];              { COM2 Empfangs-Halteregister ausl. }
  Port[$20]:=$20;                       { EOI-Signal einmal aussenden }

{-------Modem-Steuerregister setzen ----------------}
  if (Direct in ['E','D']) then
    Port[ComBasis+4]:=11                { IntReq EIN }
  else
    Port[ComBasis+4]:=3;                { IntReq AUS }

ComSelect:=ComNr;
end;

Liebe Grüße aus dem schönen Oberharz

Tom vom Berg

--
 ☻_
/▌
/ \ Nur selber lernen macht schlau
http://bergpost.annerschbarrich.de