HTTP2: Unterschied zwischen den Versionen

Aus OrgaMon Wiki
Zur Navigation springen Zur Suche springen
 
(98 dazwischenliegende Versionen von 2 Benutzern werden nicht angezeigt)
Zeile 1: Zeile 1:
* Im Moment entsteht der OrgaMon-HTTP2 Server in FreePascal auf GitHub.  
* Das Zukunftsprojekt [[Polyzalos]] erfordert die Integration eines HTTP/2 Servers in OrgaMon
* Eine erste Alpha Version ist auf github erschienen
* Im Moment entsteht deshalb ein HTTP/2 Server in FreePascal, Zielsystem ist im Moment auf win64 beschränkt
* Alle Quelltexte befinden sich auf GitHub
** [[https://github.com/Andreas-Filsinger/OrgaMon/blob/main/PASconTools/cryptossl.pas cryptossl.pas]]
** [[https://github.com/Andreas-Filsinger/OrgaMon/blob/main/PASconTools/hpack.pas hpack.pas]]
** [[https://github.com/Andreas-Filsinger/OrgaMon/blob/main/PASconTools/http2.pas http2.pas]]


https://github.com/Andreas-Filsinger/OrgaMon-HTTP2
== Inbetriebnahme ==


 
=== openSSL ===
=== Inbetriebnahme ===
 
==== openSSL ====


Windows
Windows


* http://slproweb.com/products/Win32OpenSSL.html
* http://slproweb.com/products/Win32OpenSSL.html
* Downloade und Installiere die 64bit Light Version (im Moment "Win64 OpenSSL v1.1.1 Light" .exe)
* Downloade und Installiere die 64bit Light Version (im Moment "Win64 OpenSSL v3.2.0 Light" .exe)
** Standard-Ziel akzeptieren, "in das Systemverzeichnis" angekreuzt lassen
** Standard-Ziel akzeptieren, "in das Systemverzeichnis" angekreuzt lassen


Zeile 19: Zeile 20:
* selbst aus den Quellen compilieren, da zumeist 1.0 Teil der Distributionen ist
* selbst aus den Quellen compilieren, da zumeist 1.0 Teil der Distributionen ist


==== Zertifikat ====
=== Zertifikat ===
 
==== localhost ====


* mit openssl erst mal key.pem und cert.pem erstellen (hier im Beispiel für die Server-Identität "localhost")
* mit openssl erst mal key.pem und cert.pem erstellen (hier im Beispiel für die Server-Identität "localhost")
** <code>openssl req -x509 -nodes -newkey rsa:4096 -keyout key.pem -out cert.pem -days 365 -subj '/CN=<b><i>localhost</i></b>'</code>
** <code>openssl req -x509 -nodes -newkey rsa:4096 -keyout key.pem -out cert.pem -days 365 -subj '/CN=<b><i>localhost</i></b>'</code>
#
#
#
openssl req -x509 -out localhost.crt -keyout localhost.key  -newkey rsa:2048 -nodes -days 365 -sha256  -subj '/CN=localhost' -extensions EXT -config <( \
printf "[dn]\nCN=localhost\n[req]\ndistinguished_name = dn\n[EXT]\nsubjectAltName=DNS:localhost\nkeyUsage=digitalSignature\nextendedKeyUsage=serverAuth")
* ein Hauptverzeichnis ausdenken und dort ein Verzeichnis pro CN erstellen
* ein Hauptverzeichnis ausdenken und dort ein Verzeichnis pro CN erstellen
* jeweils die 2 Dateien dort rein
* jeweils die 2 Dateien dort rein
Zeile 38: Zeile 49:
       cert.pem
       cert.pem


==== Port 443 auf dem eigenen System öffnen ====
* Zertifikat in Google Chrome installieren
** Einstellung -> Sicherheit und Datenschutz -> Sicherheit -> Zertifikate verwalten -> Reiter "Vertrauenswürdige Stammzertifizierungsstellen" -> Importieren ->
 
==== local.orgamon.net ====
 
* Ich habe bereits ein letsencrypt *.orgamon.net Zertifikat
* Ich habe (bei schlundtech) "local.orgamon.net" auf 127.0.0.1 zeigen lassen (A-Record)
* Ich habe in der Fritz!Box die Ausnahme für den lokalen Rebindschutz eingetragen (für "local.orgamon.net")
* privkey.pem und cert.pem kann ich so für den Webserver nutzen
* Meine Entwicklungsumgebung kann somit die lokale Maschine sein, obwohl ich eine richtige Domain angebe deren Namensauflösung im Web läuft
 
==== On demand cert generation ====
 
* Generiere doch ein key/cert für computername.local
 
https://github.com/marsupilami79/zeoslib/blob/master/src/webservice/server/dbcproxycertstore.pas
 
=== Port 443 auf dem eigenen System öffnen ===


Wenn Du einen von aussen sichtbaren Webserver (HTTPS) auf dem eigenen Rechner betreiben willst musst Du Port :443 öffnen.
Wenn Du einen von aussen sichtbaren Webserver (HTTPS) auf dem eigenen Rechner betreiben willst musst Du Port :443 öffnen.
Zeile 47: Zeile 75:
* Auf deinem Router musst Du eingehenden Netzwerkverkehr auf Port :443 auf deinen lokalen Rechner leiten (AVM nennt das "Freigabe")
* Auf deinem Router musst Du eingehenden Netzwerkverkehr auf Port :443 auf deinen lokalen Rechner leiten (AVM nennt das "Freigabe")


=== Informationsquellen ===
=== polyzalosd ===
 
* Diese Konsolenanwendung gibt Statusmeldungen (Log) in Farbe aus
* dies muss unter Windows jedoch aktiviert werden
 
reg add HKEY_CURRENT_USER\Console /v VirtualTerminalLevel /t REG_DWORD /d 0x00000001 /f
 
* https://ss64.com/nt/syntax-ansi.html


==== RFC ====
{{Anmerkung|Dies macht polyzalosd inzwischen über eine Windows-API Funktion selbst}}


* <b>HPACK</b> https://tools.ietf.org/html/rfc7541
== Informationsquellen ==
* <b>HTTP/2</b> https://tools.ietf.org/html/rfc7540


==== HTTP/2 ====
=== HPACK ===


* RFC <b>HPACK</b> https://tools.ietf.org/html/rfc7541
=== HTTP/2 ===
* RFC <b>HTTP/2</b> https://datatracker.ietf.org/doc/html/rfc9113
** veraltet: <b>HTTP/2</b> https://tools.ietf.org/html/rfc7540
* https://github.com/nghttp2/nghttp2
* https://github.com/nghttp2/nghttp2
** https://nghttp2.org/blog/2014/04/27/how-dependency-based-prioritization-works/
* https://github.com/nginx/nginx
* https://github.com/nginx/nginx
* https://github.com/h2o/h2o
=== Design ===
* https://calendar.perfplanet.com/2020/head-of-line-blocking-in-quic-and-http-3-the-details/
* Der Client stellt eine Menge Requests, der erste Response (16 MB gross) verstopft aber die sende Richtung
** die folgenden Responses hätten aber nur minimal kleine Antworten benötigt, also z.B. HTTP 304
** dann blockiert der lange Response alles andere
** in der Aufbau-Phase einer Seite wäre es gut der Server hätte eine Kenntniss davon was der Client alles braucht
** Es ist ja eigentlich klar war ein "full" Reload benötigt, und da sollte man multiplexen solange noch nicht alle Antworten durch sind


==== TLS ====
=== TLS ===


* https://wiki.openssl.org/index.php/Simple_TLS_Server
* https://wiki.openssl.org/index.php/Simple_TLS_Server
Zeile 68: Zeile 119:
* http://gnutls.org/manual/gnutls.html#Server-name-indication
* http://gnutls.org/manual/gnutls.html#Server-name-indication
* https://github.com/jay/http2_blacklisted_ciphers
* https://github.com/jay/http2_blacklisted_ciphers
* https://wiki.openssl.org/index.php/TLS1.3


=== Konzept ===
=== Konzept ===
Zeile 74: Zeile 126:
* cOrgaMon ist ein https:// Server nach HTTP/2 Standard ohne UI
* cOrgaMon ist ein https:// Server nach HTTP/2 Standard ohne UI
* <u>eine</u> Instanz von cOrgaMon kümmert sich um <u>eine</u> langbestehende TCP-Clientverbindung (KEEP_ALIVE)
* <u>eine</u> Instanz von cOrgaMon kümmert sich um <u>eine</u> langbestehende TCP-Clientverbindung (KEEP_ALIVE)
* HTTPS:// TLS 1.2 (nichts anderes!) TLS 1.3 wenn von openSSL angeboten wird
* HTTPS:// TLS 1.3 (nichts anderes!)  
* Clients, die NICHT die "Server Name Indication (SNI) extension" liefern werden abgelehnt
* Clients, die NICHT die "Server Name Indication (SNI) extension" liefern werden abgelehnt
* Target ist win64 und linux
* Target ist win64 und linux
* openSSL Lib der Version 1.1 "e" oder besser wird verwendet
* openSSL Lib der Version 3.1 oder besser wird verwendet
* die Verbindung bleibt ständig bestehen
* die Verbindung bleibt ständig bestehen
* Test https://tools.keycdn.com/http2-test
* Test https://tools.keycdn.com/http2-test
Zeile 184: Zeile 236:
  FRAME_PRIORITY
  FRAME_PRIORITY
   Stream 11.3 has 0
   Stream 11.3 has 0
==== openSSL - Installation ====
* der HTTP/2 server benötigt OpenSSL für den Verbindungsaufbau zum Client
wget https://www.openssl.org/source/openssl-1.1.0d.tar.gz
tar -xzf openssl-1.1.0d.tar.gz
cd openssl-1.1.0d/
./config
make
cp -p libcrypto.so.1.1 /usr/lib64
cp -p libssl.so.1.1 /usr/lib64
* Prüfen, welche API zur Verfügung gestellt wird
nm --defined-only -g /usr/lib64/libssl.so.1.1 >libssl.def


==== HMUX ====
==== HMUX ====
Zeile 235: Zeile 269:
* https://github.com/Lone-Coder/letsencrypt-win-simple/releases
* https://github.com/Lone-Coder/letsencrypt-win-simple/releases


== nginx ==
== Paralleles Arbeiten ==
 
=== 1. Stufe (unbekannter Sinn) ===
 
2018/11/06 15:20:43 [debug] 1039#1039: *1 http2 frame out: 01380990 sid:0 bl:0 len:0
2018/11/06 15:20:43 [debug] 1039#1039: *1 http2 frame out: 01380900 sid:0 bl:0 len:4
2018/11/06 15:20:43 [debug] 1039#1039: *1 http2 frame out: 01380870 sid:0 bl:0 len:18
2018/11/06 15:20:43 [debug] 1039#1039: *1 malloc: 013B61B8:16384
2018/11/06 15:20:43 [debug] 1039#1039: *1 SSL buf copy: 27
2018/11/06 15:20:43 [debug] 1039#1039: *1 SSL buf copy: 13
2018/11/06 15:20:43 [debug] 1039#1039: *1 SSL buf copy: 9
2018/11/06 15:20:43 [debug] 1039#1039: *1 SSL to write: 49
2018/11/06 15:20:43 [debug] 1039#1039: *1 SSL_write: 49
2018/11/06 15:20:43 [debug] 1039#1039: *1 http2 frame sent: 01380870 sid:0 bl:0 len:18
2018/11/06 15:20:43 [debug] 1039#1039: *1 http2 frame sent: 01380900 sid:0 bl:0 len:4
2018/11/06 15:20:43 [debug] 1039#1039: *1 http2 frame sent: 01380990 sid:0 bl:0 len:0
 
 
=== 2. Stufe (Header) ===
 
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 output header: ":status: 200"
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 output header: "server: nginx/1.15.5"
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 output header: "date: Tue, 06 Nov 2018 14:20:46 GMT"
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 output header: "content-type: text/html; charset=UTF-8"
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2:15 create HEADERS frame 013B7A80: len:57 fin:0
2018/11/06 15:20:46 [debug] 1039#1039: *1 http cleanup add: 013B7B40
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 frame out: 013B7A80 sid:15 bl:1 len:57
2018/11/06 15:20:46 [debug] 1039#1039: *1 malloc: 013C1B78:16384
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL buf copy: 9
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL buf copy: 57
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2:15 HEADERS frame 013B7A80 was sent
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 frame sent: 013B7A80 sid:15 bl:1 len:57
 
=== 3. Stufe (Data) ===
 
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2:15 create DATA frame 013B7A80: len:8128 flags:0
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 frame out: 013B7A80 sid:15 bl:0 len:8128
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL buf copy: 9
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL buf copy: 4032
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL buf copy: 4096
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL to write: 8203
#
# Gemeinsames Senden von "HEADER" + "DATA"
#
2018/11/06 15:20:46 [debug] 1039#1039: *1 SSL_write: 8203
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2:15 DATA frame 013B7A80 was sent
2018/11/06 15:20:46 [debug] 1039#1039: *1 http2 frame sent: 013B7A80 sid:15 bl:0 len:8128
 
=== Paralleles Arbeiten ===




* Ein einzelner OrgaMon-Prozess ist für eine dauerhafte TCP/Connection zuständig
* Ein einzelner OrgaMon-Prozess ist für eine dauerhafte TCP/Connection zuständig
* Ich denke dass mit OpenSSL 3.5 QUIC Server Support kommt (https://github.com/openssl/openssl/commit/cb629550cdab518c925e9b402e11b86497a03845)


==== Thread: SSL_read() ====
=== Thread: SSL_read() ===


* Ein Thread sollte SSL_read ausführen, wenn da ein Datenblock oder FRAME fertig ist, sollte dieser als "EventProc" an den Main-Thread übergeben werden
* Ein Thread sollte SSL_read ausführen, wenn da ein Datenblock oder FRAME fertig ist, sollte dieser als "EventProc" an den Main-Thread übergeben werden
** https://github.com/BeRo1985/pasmp
** https://github.com/BeRo1985/pasmp


==== Thread: JOBs ====
=== Thread: JOBs ===


* Möglicherweise startet OrgaMon wiederum SubProgramme mit langen Laufzeiten, diese SubProgramme schreiben Status Infos in memcached
* Möglicherweise startet OrgaMon wiederum SubProgramme mit langen Laufzeiten, diese SubProgramme schreiben Status Infos in memcached
* Rückmeldungen dieser lang laufenden Prozesse ev. über https://developer.mozilla.org/de/docs/Web/API/Push_API
* Rückmeldungen dieser lang laufenden Prozesse ev. über https://developer.mozilla.org/de/docs/Web/API/Push_API


=== Pascal -> JavaScript ===
== Pascal -> JavaScript ==


Durch den Wegfall der GUI muss Code auf der Client GUI autark laufen können. Dieser soll im OrgaMon Programm als FreePascal-Code aufnotiert werden, die compilierung teilt den Code auf (Client Code / Server Code) und verteilt das Java-Script über den HTTP2 Server. Freepascal hat schon eine Implementierung die Pascal nach JS ermöglicht.
Durch den Wegfall der GUI muss Code auf der Client GUI autark laufen können. Dieser soll im OrgaMon Programm als FreePascal-Code aufnotiert werden, die compilierung teilt den Code auf (Client Code / Server Code) und verteilt das Java-Script über den HTTP2 Server. Freepascal hat schon eine Implementierung die Pascal nach JS ermöglicht.
Zeile 351: Zeile 338:
* In einer Datenbank soll das Know-How für die Web Objekte gespeichert sein
* In einer Datenbank soll das Know-How für die Web Objekte gespeichert sein


=== Retry-, Reconnect- Fähig ===
== Retry-, Reconnect- Fähig ==


* immer eine lang stehende Keep-Alive TCP Verbindung, mit "Full Reconnect"- und "Client-IP-Change"- Möglichkeit
* immer eine lang stehende Keep-Alive TCP Verbindung, mit "Full Reconnect"- und "Client-IP-Change"- Möglichkeit
Zeile 359: Zeile 346:
* Der HTTP/2 Server soll eine Modus haben, wo er nur EINE Verbindung EINER IP akzetiert
* Der HTTP/2 Server soll eine Modus haben, wo er nur EINE Verbindung EINER IP akzetiert


=== Meilensteine ===
== Meilensteine ==


08.12.2023 Feature Freeze: Funktionalität für ServiceWorker und sqlite3.wasm Test ausreichend
01.12.2023 RFC: "WINDOW_UPDATE" verbessert
26.11.2023 erster "polyzalosd.exe" mit Setup für Win64
18.11.2023 Server läuft als Konsolen-App
14.11.2023 Auslieferung von DATA>MAX_FRAME_SIZE
10.11.2023 openSSL 3.1.4 mit TLS 1.3, erstmals von der RFC 9113 erfahren, Festlegung auf Chrome als Client
24.02.2022 openSSL 3.0.1 mit TLS 1.3
13.10.2021 Umstellung auf OpenSSL 3, bisher noch mit ACCEPT Fehler
23.10.2020 erste Seite wird ausgeliefert
12.11.2018 FRAME / HPACK decoding im laufenden Betrieb möglich
08.11.2018 Firefox 63 macht leider keine TLS 1.3 Verbindung, aber immerhin TLS 1.2
  26.06.2018 Firefox 61 mit nativ aktiviertem TLS 1.3 ist erschienen
  26.06.2018 Firefox 61 mit nativ aktiviertem TLS 1.3 ist erschienen
  24.11.2017 Erster Client Hello via Read-Thread
  24.11.2017 Erster Client Hello via Read-Thread
Zeile 366: Zeile 364:
  14.08.2017 Erster Client Hello von Firefox
  14.08.2017 Erster Client Hello von Firefox


=== todo ===
== todo ==
 
SETTINGS ACK!
* Linux Version
nach HEADER_TABLE_SIZE dann so eine TABLE erstellen
* HTTP/2 erste Login Seite
HEADERS und DATA an den richtigen STREAM senden! Content!!!
* OLAP -> Migration auf Console
HPACK encoder
* Auswertung -> Migration auf Console
STREAM Objekt
* OrgaMon Workflow Sheet?!
HTTP2 Objekt
* OpenSSL QUIC Server Integration
 
== Screen-Shots ==
 
[[Datei:PolyZalos-0.png|200px]]

Aktuelle Version vom 3. November 2024, 15:37 Uhr

  • Das Zukunftsprojekt Polyzalos erfordert die Integration eines HTTP/2 Servers in OrgaMon
  • Im Moment entsteht deshalb ein HTTP/2 Server in FreePascal, Zielsystem ist im Moment auf win64 beschränkt
  • Alle Quelltexte befinden sich auf GitHub

Inbetriebnahme

openSSL

Windows

Linux

  • selbst aus den Quellen compilieren, da zumeist 1.0 Teil der Distributionen ist

Zertifikat

localhost

  • mit openssl erst mal key.pem und cert.pem erstellen (hier im Beispiel für die Server-Identität "localhost")
    • openssl req -x509 -nodes -newkey rsa:4096 -keyout key.pem -out cert.pem -days 365 -subj '/CN=localhost'
# 
#
#
openssl req -x509 -out localhost.crt -keyout localhost.key   -newkey rsa:2048 -nodes -days 365 -sha256   -subj '/CN=localhost' -extensions EXT -config <( \
printf "[dn]\nCN=localhost\n[req]\ndistinguished_name = dn\n[EXT]\nsubjectAltName=DNS:localhost\nkeyUsage=digitalSignature\nextendedKeyUsage=serverAuth")


  • ein Hauptverzeichnis ausdenken und dort ein Verzeichnis pro CN erstellen
  • jeweils die 2 Dateien dort rein
  • Beispiel: Dein Server ist als "localhost" auf der Maschine selbst, und als "rom" im eigenen Netz, und als "orgamon-2.dyndns.org" von aussen ansprechbar, dann must Du 3x openssl rifen wir oben angegeben mit wechselnder CN
\srv\hosts\
  .\localhost\
     key.pem
     cert.pem
  .\rom\
     key.pem
     cert.pem
  .\orgamon-2.dyndns.org\
     key.pem
     cert.pem
  • Zertifikat in Google Chrome installieren
    • Einstellung -> Sicherheit und Datenschutz -> Sicherheit -> Zertifikate verwalten -> Reiter "Vertrauenswürdige Stammzertifizierungsstellen" -> Importieren ->

local.orgamon.net

  • Ich habe bereits ein letsencrypt *.orgamon.net Zertifikat
  • Ich habe (bei schlundtech) "local.orgamon.net" auf 127.0.0.1 zeigen lassen (A-Record)
  • Ich habe in der Fritz!Box die Ausnahme für den lokalen Rebindschutz eingetragen (für "local.orgamon.net")
  • privkey.pem und cert.pem kann ich so für den Webserver nutzen
  • Meine Entwicklungsumgebung kann somit die lokale Maschine sein, obwohl ich eine richtige Domain angebe deren Namensauflösung im Web läuft

On demand cert generation

  • Generiere doch ein key/cert für computername.local

https://github.com/marsupilami79/zeoslib/blob/master/src/webservice/server/dbcproxycertstore.pas

Port 443 auf dem eigenen System öffnen

Wenn Du einen von aussen sichtbaren Webserver (HTTPS) auf dem eigenen Rechner betreiben willst musst Du Port :443 öffnen.

  • Auf deinem Router brauchst Du eine feste IP oder ein Dyndns
  • Auf deinem Router musst Du eingehenden Netzwerkverkehr auf Port :443 auf deinen lokalen Rechner leiten (AVM nennt das "Freigabe")

polyzalosd

  • Diese Konsolenanwendung gibt Statusmeldungen (Log) in Farbe aus
  • dies muss unter Windows jedoch aktiviert werden
reg add HKEY_CURRENT_USER\Console /v VirtualTerminalLevel /t REG_DWORD /d 0x00000001 /f
Light bulb  Hinweis:  Dies macht polyzalosd inzwischen über eine Windows-API Funktion selbst

Informationsquellen

HPACK

HTTP/2

Design

  • https://calendar.perfplanet.com/2020/head-of-line-blocking-in-quic-and-http-3-the-details/
  • Der Client stellt eine Menge Requests, der erste Response (16 MB gross) verstopft aber die sende Richtung
    • die folgenden Responses hätten aber nur minimal kleine Antworten benötigt, also z.B. HTTP 304
    • dann blockiert der lange Response alles andere
    • in der Aufbau-Phase einer Seite wäre es gut der Server hätte eine Kenntniss davon was der Client alles braucht
    • Es ist ja eigentlich klar war ein "full" Reload benötigt, und da sollte man multiplexen solange noch nicht alle Antworten durch sind

TLS

Konzept

  • cOrgaMon ist ein https:// Server nach HTTP/2 Standard ohne UI
  • eine Instanz von cOrgaMon kümmert sich um eine langbestehende TCP-Clientverbindung (KEEP_ALIVE)
  • HTTPS:// TLS 1.3 (nichts anderes!)
  • Clients, die NICHT die "Server Name Indication (SNI) extension" liefern werden abgelehnt
  • Target ist win64 und linux
  • openSSL Lib der Version 3.1 oder besser wird verwendet
  • die Verbindung bleibt ständig bestehen
  • Test https://tools.keycdn.com/http2-test

Implementierung TCP

Test

Sollte dein cOrgaMon-Host ROM heissen:

  • openssl s_client -debug -servername rom -connect rom:443

Sollte interessant sein, was der Server so liefert, kann man das in eine Datei umleiten:


#
# openssl s_client -servername rom -nextprotoneg "h2,h3" -sess_out out.http2 -connect rom:443 >o.http2
#

#
# hexdump -C o.http2
# (leider ist ein openssl interner Prefix nicht vermeidbar, aber ab einer gewissen Position gehts los!)
#

00000df0  28 73 65 6c 66 20 73 69  67 6e 65 64 20 63 65 72  |(self signed cer|
00000e00  74 69 66 69 63 61 74 65  29 0a 2d 2d 2d 0a 50 52  |tificate).---.PR|
00000e10  49 20 2a 20 48 54 54 50  2f 32 2e 30 0d 0a 0d 0a  |I * HTTP/2.0....|
00000e20  53 4d 0d 0a 0d 0a 00 00  18 04 00 00 00 00 00 00  |SM..............|
00000e30  01 00 00 10 00 00 03 00  00 00 65 00 04 00 00 ff  |..........e.....|
00000e40  ff 00 05 00 10 00 00 00  00 04 08 00 00 00 00 00  |................|
00000e50  00 0a 00 00                                       |....|
00000e54

Aufbau

HTTP2

  • Zentrale Steuerunit für den HTTP2 Server
  • Öffnet und Schliesst die Verbindung, dabei wird die openSSL entsprechend Konfiguriert
  • Beobachtet die Verbindungsaushandlung
  • Lehnt ungeeignetes ab
  • Verhindert Fallbacks in unsichere Technik
  • Verarbeitet den Server-Domain Namen Callback
  • Stellt .pem und .cert zur Verfügung
  • implementiert den Datenmultiplexer laut RFC, fügt also den fragmentierten Netzwerkverkehr wieder in geordnete Bahnen
  • Feuert Events wenn Daten "fertig" vorliegen an HTTP2

typischer HTTP/2 Content am Anfang der Verbindung.

Client -> Server

50 52 49 20 2A 20 48 54 54 50 2F 32 2E 30 0D 0A  PRI.*.HTTP/2.0..
0D 0A 53 4D 0D 0A 0D 0A 
00 00 12 (18 Bytes Content)
04 00 00 00 00 00 SETTINGS, also 3 Settings!)
00 01 00 01 00 00 
00 04 00 02 00 00
00 05 00 00 40 00
00 00 04 (4 Bytes content)
08 00 00 00 00 00 WINDOW_UPDATE
00 BF 00 01  
00 00 05 (5 Bytes Content)
02 00 00 00 00 03 PRIO
00 00 00 00 C8
00 00 05 (5 Bytes Content)
02 00 00 00 00 05 PRIO
00 00 00 00 64
00 00 05 (5 Bytes Content)
02 00 00 00 00 07 PRIO
00 00 00 00 00
00 00 05 (5 Bytes Content)
02 00 00 00 00 09  PRIO
00 00 00 07 00
00 00 05 (5 Bytes Content)
02 00 00 00 00 0B PRIO
00 00 00 03 00 
 

FRAME_SETTINGS
 HEADER_TABLE_SIZE 65536
 INITIAL_WINDOW_SIZE 131072
 MAX_FRAME_SIZE 16384
FRAME_WINDOW_UPDATE
 0 has Window_Size_Increment 12517377
FRAME_PRIORITY
 Stream 3.0 has 200
FRAME_PRIORITY
 Stream 5.0 has 100
FRAME_PRIORITY
 Stream 7.0 has 0
FRAME_PRIORITY
 Stream 9.7 has 0
FRAME_PRIORITY
 Stream 11.3 has 0

HMUX

Entfällt, wurde in HTTP2 integriert

HPACK

  • implementiert die Header Compression laut RFC

cryptossl

  • spricht mit der openSSL Bibliothek und implementiert dabei nur was gebraucht wird.

Informationsquellen

Schritt für Schritt mit Lets Encrypt

Wir sind als in Besitz einer Domain und haben es geschafft Port 80 auf die eigene WIndows 10 Kiste zu lenken

Paralleles Arbeiten

Thread: SSL_read()

  • Ein Thread sollte SSL_read ausführen, wenn da ein Datenblock oder FRAME fertig ist, sollte dieser als "EventProc" an den Main-Thread übergeben werden

Thread: JOBs

Pascal -> JavaScript

Durch den Wegfall der GUI muss Code auf der Client GUI autark laufen können. Dieser soll im OrgaMon Programm als FreePascal-Code aufnotiert werden, die compilierung teilt den Code auf (Client Code / Server Code) und verteilt das Java-Script über den HTTP2 Server. Freepascal hat schon eine Implementierung die Pascal nach JS ermöglicht.

Details:

  • Die Tatsache "JavaScript" auf der Clientside wird der Lazarus-IDE scheinbar verheimlicht
    • Es muss also der Pascalcode in JavaScript umgewandelt werden
    • Für den Client muss eine Art Code-Lib zur Verfügung stehen, die Pascal rufen kann und umgekehrt
  • Die IDE soll denken/vorleben das Client-Seitig auch "Pascal" gesprochen wird
    • Debugging: Hier muss der WebClient in den remote-Debugging Modus gebracht werden
    • Es könnte die Infrastruktur der "Source maps" verwendet werden, also "komprimierte" Zeilen des JavaScript Quellcodes zeigen auf die entsprechenden Zeilen, die in FreePascal formuliert sind. Es werden also "fake"-Source-Maps zur Verfügung gestellt, so das eine korrekte 1:1 Beziehung zwischen Pascal und Javascript bestehen kann.
    • FreePascal und die Lazarus IDE müssen lernen, dass Teile vom Quelltext "remote" executables sind
    • FreePascal Lazarus muss Möglichkeiten bieten von einem eintretendem JAvaScript Breakpoint gerufen zu werden
    • Es soll alles auch in der Lazarus IDE mit Break-Points programmierbar sein, die IDE soll ein Verständnis haben welche Zeile welchen Code verbirgt
  • Die IDE sollte den Client-Side Part ev. farblich hinterlegen?!
  • Es muss so sein, dass eine Unit weiterhin ServerSide- / ClientSide- Code mischen kann
program SimpleCalculator;

var
 Panel : TPanel;
 Button1 : TButton;
 Button2 : TButton;
 
procedure Panel.OnClick;
begin
 beep; // This goes to JavaScript Client Code
end;

procedure Button1.OnClick;
begin
 Button2.Disable; // This goes to JavaScript Client Code
end;

procedure Button1.OnClick;
begin
 Button2.Disable; // This goes to JavaScript Client Code
end;

begin
 App.add(Panel);
 App.add(Button1);
 App.add(Button2);
end.


  • die IDE soll ein Verständnis haben dass auf Client-Seite nicht "alles" Programmierbar ist
  • aus den JavaScript Parts soll über einen Dispatcher der nonGUI Code aufbar gemacht werden
  • In einer Datenbank soll das Know-How für die Web Objekte gespeichert sein

Retry-, Reconnect- Fähig

  • immer eine lang stehende Keep-Alive TCP Verbindung, mit "Full Reconnect"- und "Client-IP-Change"- Möglichkeit
  • Ein kleines Symbol oder eine Uhr, oder ich weis noch nicht, soll symbolisieren wenn es sich um eine frisch aufgebaute Verbindung handelt
  • Es. soll eine Reconnect auch visualisiert werden, oder auch ein Verbindungsende / Abbruch
  • In der Anfangszeit brauche ich aber ein Feedback das mir beweist dass NICHT immer neue TCP verbindungen aufgebaut werden
  • Der HTTP/2 Server soll eine Modus haben, wo er nur EINE Verbindung EINER IP akzetiert

Meilensteine

08.12.2023 Feature Freeze: Funktionalität für ServiceWorker und sqlite3.wasm Test ausreichend
01.12.2023 RFC: "WINDOW_UPDATE" verbessert
26.11.2023 erster "polyzalosd.exe" mit Setup für Win64
18.11.2023 Server läuft als Konsolen-App
14.11.2023 Auslieferung von DATA>MAX_FRAME_SIZE
10.11.2023 openSSL 3.1.4 mit TLS 1.3, erstmals von der RFC 9113 erfahren, Festlegung auf Chrome als Client
24.02.2022 openSSL 3.0.1 mit TLS 1.3
13.10.2021 Umstellung auf OpenSSL 3, bisher noch mit ACCEPT Fehler
23.10.2020 erste Seite wird ausgeliefert
12.11.2018 FRAME / HPACK decoding im laufenden Betrieb möglich
08.11.2018 Firefox 63 macht leider keine TLS 1.3 Verbindung, aber immerhin TLS 1.2
26.06.2018 Firefox 61 mit nativ aktiviertem TLS 1.3 ist erschienen
24.11.2017 Erster Client Hello via Read-Thread
23.08.2017 Erster Client Hello von Chrome
14.08.2017 Erster Client Hello von Firefox

todo

  • Linux Version
  • HTTP/2 erste Login Seite
  • OLAP -> Migration auf Console
  • Auswertung -> Migration auf Console
  • OrgaMon Workflow Sheet?!
  • OpenSSL QUIC Server Integration

Screen-Shots