#cs
 ----------------------------------------------------------------------------

Telnet Dateimanager
Autor: Michael Donning

Lizenz:
http://creativecommons.org/licenses/by-nc-sa/3.0/
Telnet Dateimanager von Michael Donning steht unter einer 
Creative Commons Namensnennung-Nicht-kommerziell-Weitergabe unter gleichen Bedingungen 3.0 Unported Lizenz.

 ----------------------------------------------------------------------------
#ce

;Indent: 4, Tablänge: 4

Global $version = "0.3"

#include <ButtonConstants.au3>
#include <EditConstants.au3>
#include <GUIConstantsEx.au3>
#include <GUIListView.au3>
#include <GUIImageList.au3>
#Include <GuiListBox.au3>
#include <ListViewConstants.au3>
#include <StaticConstants.au3>
#include <TabConstants.au3>
#include <WindowsConstants.au3>
#include <GuiEdit.au3>
#include <GuiButton.au3>
#include <Timers.au3>
#include <File.au3>
#include <Math.au3>
#include <Constants.au3>


;#include <Base64.au3>

AutoItSetOption("MustDeclareVars", 1)

Global $limitView=1024*1024 ;Limit maximum file size for view to 1MB
Global $limitULDL=25*1024*1024; Limit file size for ul/dl to 25MB
Global $maxSendWORecv=16384; Maximal Senden, ohne daß Echo zurückkommt (Wenn echo aktiv)

#cs
Formatierungen der directory listings (ls -l)

lsFmt[0]
       0      1 2        3               4 5   6   7   8        9                            10
drwxr-xr-x    1 0        0             181 Fri Jun 27 04:55:35 2008 Fri Jun 27 04:55:35 2008 bin

lsFmt[1]
       0     1 2   3    4   (5,6,7,8) 9          10
-rw-r--r--  1 root root 125749 2009-01-14 02:07 moduli

lsFmt[2] (Default)
      0       1 2        3               4 5   6   7   8        9   10
drwxr-xr-x    2 root     root         4096 Fri Nov 17 11:18:47 2006 bin
lrwxrwxrwx    1 root     root            8 Wed Oct 31 16:00:13 2007 tmp -> /mnt/ram
#ce

Global $lsFmt[3]=[ _
		 "([dlrwxr-]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([0-9]+)\s+([a-zA-Z]+)\s+([a-zA-Z]+)\s+([0-9]+)\s+([0-9:]+)\s+([0-9]+)\s+[a-zA-Z]+\s+[a-zA-Z]+\s+[0-9]+\s+[0-9:]+\s+[0-9]+\s+(.*)", _
		 "([dlrwxr-]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([0-9]+)\s+()()()()([0-9-]+ [0-9:]+)\s+(.*)", _
		 "([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+(.*)" _
		  ]

#Region ### START Koda GUI section ### Form=c:\programme\autoit3\koda_formdesigner\forms\telnetmanager.kxf
Global $frmMain = GUICreate("Telnet Dateimanager", 808, 667, -1, -1)
Global $Tab1 = GUICtrlCreateTab(0, 31, 804, 615, 0)
Global $TabSheet1 = GUICtrlCreateTabItem("Dateimanager")
Global $ListView1 = GUICtrlCreateListView("Dateiname|Groesse|Datum|Flags", 4, 115, 518, 495, $GUI_SS_DEFAULT_LISTVIEW)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 0, 200)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 1, 100)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 2, 140)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 3, 70)
_GUICtrlListView_JustifyColumn(GUICtrlGetHandle($ListView1), 1, 1)
GUICtrlSetFont(-1, 8, 800, 0, "MS Sans Serif")
GUICtrlSetColor(-1, 0x00FFFF)
GUICtrlSetBkColor(-1, 0x000080)
Global $lbDir = GUICtrlCreateLabel("----", 4, 87, 473, 20, $SS_SUNKEN)
GUICtrlSetFont(-1, 10, 800, 0, "MS Sans Serif")
GUICtrlSetColor(-1, 0xFFFFFF)
GUICtrlSetBkColor(-1, 0x000080)
Global $pbDirUp = GUICtrlCreateButton("Verzeichnis ^ (Strg+PgUp)", 4, 56, 137, 25, $BS_NOTIFY)
Global $pbChDir = GUICtrlCreateButton("Verzeichnis v (Enter)", 140, 56, 114, 25, $BS_NOTIFY)
Global $pbRefresh = GUICtrlCreateButton("Aktualisieren (Strg+R)", 252, 56, 114, 25, $BS_NOTIFY)
Global $pbViewFile = GUICtrlCreateButton("Anzeigen F3", 4, 616, 70, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Dateiinhalt anzeigen (nur für Textdateien geeignet!)")
Global $pbEditFile = GUICtrlCreateButton("Bearbeiten F4", 74, 616, 70, 25, $BS_NOTIFY)
Global $pbCopyFile = GUICtrlCreateButton("Kopieren F5", 144, 616, 70, 25, $BS_NOTIFY)
Global $pbRenameFile = GUICtrlCreateButton("Umben. F6", 214, 616, 70, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Datei umbenennen")
Global $pbCreateDir = GUICtrlCreateButton("Verz. Neu F7", 284, 616, 70, 25, $BS_NOTIFY)
Global $pbDeleteFile = GUICtrlCreateButton("Löschen F8", 354, 616, 70, 25, $BS_NOTIFY)
Global $lbDirs = GUICtrlCreateList("", 528, 83, 273, 279)
GUICtrlCreateLabel("Beliebte Verzeichnisse:", 528, 56, 113, 17)
Global $pbAddDir = GUICtrlCreateButton("+ -->", 480, 87, 40, 20)
Global $pbRemDir = GUICtrlCreateButton("Entf.", 700, 56, 48, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Verzeichnis aus Liste entfernen")
Global $pbCdFavDir = GUICtrlCreateButton("Cd", 748, 56, 48, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "In Verzeichnis wechseln (auch Doppelklick)")
GUICtrlCreateGroup("Text / ASCII", 528, 592, 121, 49)
Global $pbDownload = GUICtrlCreateButton("Download", 536, 608, 54, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Textdatei Telnet -> PC  (LF -> CRLF)")
Global $pbUpload = GUICtrlCreateButton("Upload", 588, 608, 54, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Textdatei PC -> Telnet (CRLF -> LF)")
GUICtrlCreateGroup("", -99, -99, 1, 1)
GUICtrlCreateGroup("Binär", 664, 592, 121, 49)
Global $pbBinDownload = GUICtrlCreateButton("Download", 672, 608, 54, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Binärdatei (z.B. Programm/Archiv/Bild)  unverändert von Telnet -> PC")
Global $pbBinUpload = GUICtrlCreateButton("Upload", 724, 608, 54, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Binärdatei (z.B. Programm/Archiv/Bild) unverändert von PC -> Telnet")
GUICtrlCreateGroup("", -99, -99, 1, 1)
Global $lvMount = GUICtrlCreateListView("Mount|Fs|Größe(MB)|rw|Belegt", 528, 392, 273, 190)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 0, 90)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 1, 75)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 2, 65)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 3, 40)
GUICtrlSendMsg(-1, $LVM_SETCOLUMNWIDTH, 4, 50)
_GUICtrlListView_JustifyColumn(GUICtrlGetHandle($lvMount), 2, 1)
GUICtrlCreateLabel("Mount / FS:", 528, 368, 61, 17)
Global $pbCdMount = GUICtrlCreateButton("Cd", 748, 366, 48, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "In Verzeichnis wechseln")
Global $pbRefreshMount = GUICtrlCreateButton("Aktu.", 700, 366, 48, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Liste aktualisieren")
Global $pbFileAttr = GUICtrlCreateButton("Attribute F9", 424, 616, 70, 25, $BS_NOTIFY)
GUICtrlSetTip(-1, "Dateiattribute setzen")
Global $TabSheet2 = GUICtrlCreateTabItem("Telnet")
Global $eTelnet = GUICtrlCreateEdit("", 8, 87, 649, 529, $GUI_SS_DEFAULT_EDIT)
GUICtrlSetData(-1, "")
Global $pbCtrlC = GUICtrlCreateButton("Strg+C = Abbruch", 56, 616, 99, 21)
Global $pbSendTelnet = GUICtrlCreateButton("&Senden (Enter)", 8, 64, 80, 21, $BS_NOTIFY)
Global $eSendTelnet = GUICtrlCreateInput("", 92, 64, 561, 21, $GUI_SS_DEFAULT_INPUT)
Global $pbClear = GUICtrlCreateButton("Leeren", 4, 616, 51, 21, $BS_NOTIFY)
Global $pbCtrlD = GUICtrlCreateButton("Strg+D = EOF", 152, 616, 99, 21)
Global $pbAddFilename = GUICtrlCreateButton("", 656, 64, 144, 21)
Global $TabSheet3 = GUICtrlCreateTabItem("Info / Einstellungen")
GUICtrlSetState(-1,$GUI_SHOW)
GUICtrlCreateGroup(" Wichtiger Hinweis! ", 8, 360, 785, 105)
GUICtrlCreateLabel("Vorsicht, Gefahr des Funktionsverlustes!" & @CRLF & _
   "Bei Verwendung dieses Programmes besteht grundsätzlich die Möglichkeit, daß  Geräte ihre Funktionsfähigkeit einbüßen. Sei es durch Fehlbedienung (z.B. löschen von Dateien) oder durch Fehlfunktion dieses Programmes." & @CRLF & @CRLF & _
   "Der Autor dieses Programmes übernimmt keine Haftung für sämtliche Folgen, die durch die Benutzung des Programmes 'Telnet Dateimanager' entstehen. Die Benutzung erfolgt somit auf eigene Gefahr.", 10, 375, 781, 88)
GUICtrlSetFont(-1, 8, 800, 0, "MS Sans Serif")
GUICtrlCreateGroup("", -99, -99, 1, 1)
GUICtrlCreateGroup("Info", 8, 56, 785, 105)
GUICtrlCreateLabel("Telnet Dateimanager Version: ", 16, 72, 147, 17)
Global $lblVersion = GUICtrlCreateLabel("--", 168, 72, 68, 24)
GUICtrlSetFont(-1, 8, 800, 0, "MS Sans Serif")
;Global $picLicense = GUICtrlCreatePic("" & @ScriptDir & "\CreativeCommons.gif", 16, 120, 88, 31)
CreateCCGifCtrl(16,120,88,31)
;GUICtrlSetCursor (-1, 0)
GUICtrlCreateLabel("Lizenz:", 16, 96, 37, 17)
Global $lblLicense = GUICtrlCreateLabel("Telnet Dateimanager von Michael Donning steht unter einer Creative Commons Namensnennung-Nicht-kommerziell-Weitergabe unter gleichen Bedingungen 3.0 Unported Lizenz.", 120, 112, 618, 41)
GUICtrlSetFont(-1, 8, 400, 4, "MS Sans Serif")
GUICtrlSetColor(-1, 0x000080)
GUICtrlSetCursor (-1, 0)
GUICtrlCreateGroup("", -99, -99, 1, 1)
Global $Group5 = GUICtrlCreateGroup("Einstellungen", 8, 168, 785, 185)
GUICtrlCreateLabel("IP / Hostname:", 16, 191, 76, 17, 0)
Global $eIP = GUICtrlCreateInput("", 156, 191, 201, 21, $GUI_SS_DEFAULT_INPUT)
GUICtrlCreateLabel("IP kann ggf. aus dem Setup-Bildschirm des Gerätes ermittelt werden.", 364, 192, 326, 17)
GUICtrlCreateLabel("Benutzername:", 16, 215, 75, 17, 0)
Global $eUsername = GUICtrlCreateInput("", 156, 215, 121, 21, $GUI_SS_DEFAULT_INPUT)
GUICtrlCreateLabel('Wenn Login keinen Namen/Kennw. erwartet, diese leer lassen. Für leere erwartete Logins "" verwenden.', 292, 216, 500, 17, 0)
GUICtrlCreateLabel("Kennwort: (ggf. Leer)", 16, 239, 103, 17, 0)
Global $ePassword = GUICtrlCreateInput("", 156, 239, 121, 21, BitOR($GUI_SS_DEFAULT_INPUT,$ES_PASSWORD))
GUICtrlCreateLabel("Achtung, Sicherheitsrisiko: Dieses Kennwort wird unverschlüsselt gespeichert. * fragt interaktiv", 292, 239, 500, 17, 0)
GUICtrlCreateLabel("Startverzeichnis", 16, 263, 79, 17, 0)
Global $eStartDir = GUICtrlCreateInput("", 156, 263, 121, 21, $GUI_SS_DEFAULT_INPUT)
GUICtrlCreateLabel("Editor", 16, 287, 31, 17, 0)
Global $eEditor = GUICtrlCreateInput("", 156, 287, 385, 21, $GUI_SS_DEFAULT_INPUT)
Global $pbSaveSettings = GUICtrlCreateButton("Einstellungen speichern", 16, 317, 163, 25, $BS_NOTIFY)
GUICtrlCreateGroup("", -99, -99, 1, 1)
GUICtrlCreateGroup("Wie geht das?", 8, 472, 265, 161)
GUICtrlCreateLabel("Dieses Tool soll eine bequemere Bedienung von Linux-Geräten (Busybox) ermöglichen:" & @CRLF & @CRLF & _
	  "1. IP-Adresse des Gerätes ermitteln und oben eingeben" & @CRLF & _
	  "2. Auf [Verbinden] klicken" & @CRLF & _
	  "3. Auf Seite 'Telnet' wechseln und schauen, ob die Verbindung klappt." & @CRLF & _
	  "4. Auf Seite 'Dateimanager' wechseln und loslegen", 10, 487, 261, 144)
GUICtrlCreateGroup("", -99, -99, 1, 1)
GUICtrlCreateGroup("Upload / Download", 280, 472, 513, 161)
GUICtrlCreateLabel("Der Download und insbesondere der Upload ist mit diesem Tool recht langsam und Fehler können auftreten. Daher ist es nur für kleinere Dateien (ca. <1MB) sinnvoll." & @CRLF & @CRLF & "Der Upload überschreibt eine ggf. vorhandene gleichnamige Datei im Zielverzeichnis." & @CRLF &  @CRLF & "Der Upload erfolgt zunächst in eine temporäre Datei. Nur wenn die Dateigröße paßt wird diese in die Zieldatei umbenannt" & @CRLF & @CRLF & "ASCII Upload/Download tauscht den Zeilenumbruch zwischen der Unix Welt (LF) und der DOS-Welt (CRLF). Binär-Upload/Download sollte die Dateien unverändert lassen.", 282, 487, 509, 144)
GUICtrlCreateGroup("", -99, -99, 1, 1)
GUICtrlCreateTabItem("")
Global $StatusBar = _GUICtrlStatusBar_Create($frmMain)
Dim $StatusBar_PartsWidth[2] = [200, -1]
_GUICtrlStatusBar_SetParts($StatusBar, $StatusBar_PartsWidth)
_GUICtrlStatusBar_SetText($StatusBar, "Nicht verbunden", 0)
_GUICtrlStatusBar_SetText($StatusBar, "", 1)
Global $pbConnect = GUICtrlCreateButton("Verbinden", 0, 0, 72, 25, $BS_NOTIFY)
Global $pbDisconnect = GUICtrlCreateButton("Trennen", 72, 0, 72, 25, $BS_NOTIFY)
;Dim $frmMain_AccelTable[20][2] = [["^{PGUP}", $pbDirUp],["^{PGDN}", $pbChDir],["^r", $pbRefresh],["{F3}", $pbViewFile],["{F4}", $pbEditFile],["{F5}", $pbCopyFile],["{F6}", $pbRenameFile],["{F7}", $pbCreateDir],["{F8}", $pbDeleteFile],["{F8}", $pbRemDir],["{F8}", $pbCdFavDir],["{F8}", $pbDownload],["{F8}", $pbUpload],["{F8}", $pbBinDownload],["{F8}", $pbBinUpload],["{F8}", $pbCdMount],["{F8}", $pbRefreshMount],["{F9}", $pbFileAttr],["^c", $pbCtrlC],["^d", $pbCtrlD]]
;GUISetAccelerators($frmMain_AccelTable)
;GUISetState(@SW_SHOW)
#EndRegion ### END Koda GUI section ###

Global $EnterKey = GUICtrlCreateDummy()
Global $frmMain_AccelTable[12][2] = [["^{PGUP}", $pbDirUp],["^{PGDN}", $pbChDir],["^r", $pbRefresh],["{F3}", $pbViewFile], _
		 ["{F4}", $pbEditFile],["{F5}", $pbCopyFile],["{F6}", $pbRenameFile],["{F7}", $pbCreateDir], _
		 ["{F8}", $pbDeleteFile],["{F9}", $pbFileAttr],["^d", $pbCtrlD], ["{ENTER}", $EnterKey] ] ;["^c", $pbCtrlC] entfernt, da sonst kein clipboard
GUISetAccelerators($frmMain_AccelTable)

;Global $clr_notconnected = 0xC0C0DC
;Global $clr_connected = 0xC0DCC0
Global $clr_notconnected = 0xC0C0FF
Global $clr_connected = 0xC0FFC0
_GUICtrlStatusBar_SetBkColor($StatusBar,$clr_notconnected)

; ***** Icons: *****
; Load images
Global $hListViewImages = _GUIImageList_Create(18, 18, 5, 3) ;Wpx, Hpx, color depth (2=8Bit, 5=32Bit), Options (3=1(use mask) + 2(mirror))
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 0) ;Datei
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 70) ;Textdatei
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 2) ;Programm
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 3) ;Ordner geschlossen
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 4) ;Ordner offen
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 71) ;DLL/Bibliothek (154 = Dateisymbol mit Zahnrad. -72)
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 115) ;Film
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 116) ;Musik
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 117) ;Fotos
_GUIImageList_AddIcon($hListViewImages, @SystemDir & "\shell32.dll", 146) ;Link

_GUICtrlListView_SetImageList($ListView1, $hListViewImages, 1)


; *****

GUICtrlSetState ( $TabSheet1,$GUI_DISABLE)
GUICtrlSetState ( $TabSheet2,$GUI_HIDE)

GUISetState(@SW_SHOW)

GUIRegisterMsg($WM_NOTIFY, "WM_NOTIFY")
GUIRegisterMsg($WM_COMMAND, "WM_COMMAND")

TCPStartUp()

Global $ini = @ScriptDir & "\Telnet_Dateimanager.ini"

If $CmdLine[0]>0 Then
	$ini=$CmdLine[1]
EndIf

Global $status=""
Global $prompt="***Telnettool Prompt***#"
Global $socket=-1
Global $doesecho=True
Global $hasBusybox=True ;wird bei ls geprueft
Global $hasLsFmt=-1 ;wird bei ls geprueft
Global $cmdCRLF=@CRLF ;manche Konsolen erwarten nur LF
Global $noOutput=False ;Unterdrückung der Ausgabe in "Telnet"-Tab
Global $inIO=false
Global $selItem,$selMountItem
Global $tmp
Global $lastULDLDir=@ScriptDir

GUICtrlSetData($lblVersion,$version)

ReadSettings()
ReadDirList()
_Timer_SetTimer($frmMain, 200, "PollTelnet") 

While 1
	Local $nMsg = GUIGetMsg()
	Switch $nMsg
		Case $GUI_EVENT_CLOSE
			SaveSettings()
			EvtAppClose()
			;Exit
		Case $lblLicense;, $picLicense
			ShellExecute("http://creativecommons.org/licenses/by-nc-sa/3.0/")
		Case $pbCreateDir
			$tmp=InputBox("Verzeichnis erstellen", "Verzeichnisname: ", _
								"","",300,130)
			If $tmp<>"" Then 
				MakeDir($socket,$status,$tmp)
				ReadDirectory($socket,$status)
			EndIf
		Case $pbEditFile
			If IsFileSelected() Then
				EditFileDlg($socket, $status, SelectedFileName(),SelectedFileSize())
			EndIf
		Case $pbDeleteFile
			If IsFileSelected() Then
				If MsgBox(1+32,"Wirklich Löschen?", _
				   StringFormat("Soll Die Datei '%s' wirklich gelöscht werden?",SelectedFileName()) _
					,0,$frmMain)=1 Then
					DelFile($socket,$status,SelectedFileName())
					ReadDirectory($socket,$status)
				EndIf
			Else
				If IsDirSelected() Then
					If MsgBox(1+32,"Wirklich Löschen?", _
					   StringFormat("Soll das Verzeichnis '%s' wirklich gelöscht werden?",SelectedFileName()) & _
					   @CRLF & "(Das Verzeichnis muss leer sein)", _
						0,$frmMain)=1 Then
						DelDir($socket,$status,SelectedFileName())
						ReadDirectory($socket,$status)
					EndIf
				EndIf
			EndIf
		Case $pbFileAttr
			If IsFileSelected() Or IsDirSelected() Then
				Local $dir
				Local $attr='777'
				If GetFileDirInfo($socket,$status,SelectedFileName(),$dir) Then
					If $dir[10]=SelectedFileName() Then
						$attr=LsAttrToOct($dir[0])
					EndIf
				EndIf
				
				$tmp=InputBox(StringFormat("Attribute für Datei/Verz. '%s' setzen.",SelectedFileName()), _
							  "Neuer Attributwert (777=Ausführen/Lesen/Schreiben): ", _
								$attr,"",300,130)
				If $tmp<>"" Then 
					SetAttr($socket,$status,SelectedFileName(),$tmp)
					ReadDirectory($socket,$status)
				EndIf
			EndIf
		Case $pbRenameFile
			If IsFileSelected() Then
				$tmp=InputBox(StringFormat("Datei '%s' umbenennen/verschieben",SelectedFileName()), _
							  "Umbenennen/Verschieben nach: ", _
								AddTargetDir(SelectedFileName()),"",300,130)
				If $tmp<>"" Then 
					MoveFile($socket,$status,SelectedFileName(),$tmp)
					ReadDirectory($socket,$status)
				EndIf
			EndIf
		Case $pbCopyFile
			If IsFileSelected() Then
				$tmp=InputBox(StringFormat("Datei '%s' kopieren",SelectedFileName()), _
							  "Kopieren nach: ", _
								AddTargetDir(SelectedFileName()),"",300,130)
				;$tmp=InputBox("Datei '" & SelectedFileName() & "' kopieren", "Kopieren nach: ", _
				;				AddTargetDir(SelectedFileName()),"",-1,-1,-1,-1,65535,$frmMain)
				If $tmp<>"" Then 
					CopyFile($socket,$status,SelectedFileName(),$tmp)
					ReadDirectory($socket,$status)
				EndIf
			EndIf
		Case $pbAddDir
			$tmp=StripTrailCRLF(GUICtrlRead($lbDir))
			If $tmp<>"" Then
				If _GUICtrlListBox_FindString($lbDirs,$tmp,True)=-1 Then
					_GUICtrlListBox_AddString($lbDirs,$tmp)
					WriteDirList()
				EndIf
			EndIf
		Case $pbRemDir
			If _GUICtrlListBox_GetCaretIndex($lbDirs)>1 Then
				_GUICtrlListBox_DeleteString($lbDirs,_GUICtrlListBox_GetCaretIndex($lbDirs))
				WriteDirList()
			EndIf
		Case $pbCdFavDir
			If _GUICtrlListBox_GetCaretIndex($lbDirs)>=0 Then
				ChDirGui($socket,$status,_GUICtrlListBox_GetText($lbDirs,_GUICtrlListBox_GetCaretIndex($lbDirs)))
			EndIf
		Case $pbDownload
			DownloadGui($socket,$status,True)
		Case $pbUpload
			UploadGui($socket,$status,True)
		Case $pbBinDownload
			DownloadGui($socket,$status,False)
		Case $pbBinUpload
			UploadGui($socket,$status,False)
		Case $ListView1
		Case $EnterKey
			;MsgBox(0,"Focus",_GuiCtrlGetFocus($frmMain) "/" )
			;If ControlGetFocus($frmMain) = 'eSendTelnet' 
			If _GuiCtrlGetFocus($frmMain) = $eSendTelnet Then TcpSendEcho($socket,_GUICtrlEdit_GetText($eSendTelnet) & $cmdCRLF)
			If _GuiCtrlGetFocus($frmMain) = $ListView1 Then ListViewChDir()
		Case $pbAddFilename
			If SelectedFileName()<>"" Then
				_GUICtrlEdit_AppendText($eSendTelnet,' "' & SelectedFileName() & '"')
			EndIf
		Case $pbSendTelnet
			TcpSendEcho($socket,_GUICtrlEdit_GetText($eSendTelnet) & $cmdCRLF)
		Case $pbClear
			_GUICtrlEdit_SetText($eTelnet,"")
		Case $pbCtrlC
			TcpSendEcho($socket,Chr(3))
		Case $pbCtrlD
			TcpSendEcho($socket,Chr(4))
		Case $pbViewFile
			If IsFileSelected() Then
				ViewFile($socket,$status,SelectedFileName(),SelectedFileSize())
			EndIf
		Case $pbChDir
			ListViewChDir()
		Case $pbCdMount
			lvMountChDir()
		Case $pbDirUp
			ChDirGui($socket,$status,"..")
		Case $pbRefreshMount
			ReadMounts($socket,$status)
		Case $pbRefresh
			ReadDirectory($socket,$status)
		Case $pbConnect
			$socket = TelnetConnect(GUICtrlRead($eIP),GUICtrlRead($eUsername),GUICtrlRead($ePassword),$status)
			If $status<>"" Then
				MsgBox(0,"Verbindungsfehler IP & Benutzer korrekt? ",$status,0,$frmMain)
			Else
				If GUICtrlRead($eStartDir)<>"" Then
					ChDirGui($socket,$status,GUICtrlRead($eStartDir))
				Else
					$pwd=GetPWD($socket,$status)
					If $status="" Then ReadDirectory($socket,$status)
				EndIf
				If $status="" Then ReadMounts($socket,$status)
			EndIf
		Case $pbDisconnect
			TelnetDisconnect($socket)
		Case $pbSaveSettings
			SaveSettings()
	EndSwitch
WEnd

Func SaveSettings()
	Local $sect = "Settings"
	IniWrite($ini,$sect,"IP",GUICtrlRead($eIP))
	IniWrite($ini,$sect,"User",GUICtrlRead($eUsername))
	IniWrite($ini,$sect,"Password",GUICtrlRead($ePassword))
	IniWrite($ini,$sect,"StartDir",GUICtrlRead($eStartDir))
	IniWrite($ini,$sect,"LastULDLDir",$lastULDLDir)
	IniWrite($ini,$sect,"Editor",GUICtrlRead($eEditor))
EndFunc

Func StripTrailCRLF($str)
	Return StringRegExpReplace($str,"[\r\n]*","")
EndFunc

;Zielverzeichnis (anhand Liste rechts) hinzufügen
Func AddTargetDir($str)
	Local $target=""
	If _GUICtrlListBox_GetCaretIndex($lbDirs)>0 Then ;index0 = "." -> ignorieren
		$target=_GUICtrlListBox_GetText($lbDirs,_GUICtrlListBox_GetCaretIndex($lbDirs)) & "/"
	EndIf
	Return $target & $str
EndFunc

Func ReadSettings()
	Local $sect = "Settings"
	
	;Default IP
	Local $ipdef
	Local $ipspl = stringsplit(@ipaddress1,".")
	;bei Localhost die 2. nehmen
	If $ipspl[1]="127" Then $ipspl = stringsplit(@IPAddress2,".")
	If $ipspl[1]<>"" Then
		$ipdef = $ipspl[1] & "." & $ipspl[2] & "." & $ipspl[3] & "."
	Else
		$ipdef=""
	EndIf
		
	
	GUICtrlSetData($eIP,IniRead($ini,$sect,"IP",$ipdef))
	GUICtrlSetData($eUsername,IniRead($ini,$sect,"User","root"))
	GUICtrlSetData($ePassword,IniRead($ini,$sect,"Password",""))
	GUICtrlSetData($eStartDir,IniRead($ini,$sect,"StartDir","/"))
	$lastULDLDir=IniRead($ini,$sect,"LastULDLDir",$lastULDLDir)
	GUICtrlSetData($eEditor,IniRead($ini,$sect,"Editor","Notepad.Exe"))
EndFunc

;Beliebte Verzeichnisse aus INI
Func WriteDirList()
	Local $i
	Local $sect = "Directories"
	IniWrite($ini,$sect,"NumEntries",_GUICtrlListBox_GetCount($lbDirs))
	For $i=0 To _GUICtrlListBox_GetCount($lbDirs)-1
		IniWrite($ini,$sect,"Entry" & $i,StripTrailCRLF(_GUICtrlListBox_GetText($lbDirs, $i)))
	Next
	IniDelete($ini,$sect,"Entry"&_GUICtrlListBox_GetCount($lbDirs)) ;Falls ein Eintrag geloscht wurde, letzten löschen
EndFunc

;Beliebte Verzeichnisse in INI
Func ReadDirList()
	Local $i
	Local $sect = "Directories"
	Local $cnt
	$cnt=IniRead($ini,$sect,"NumEntries","0")
	If $cnt=0 Then
		;Default Einträge (zwecks copy in aktuelles/updir)
		_GUICtrlListBox_AddString($lbDirs, ".")
		_GUICtrlListBox_AddString($lbDirs, "..")
	Else
		_GUICtrlListBox_BeginUpdate($lbDirs)
		_GUICtrlListBox_ResetContent($lbDirs)
		For $i = 0 To $cnt-1
			;MsgBox(0,"Hallo","<" & IniRead($ini,$sect,"Entry" & $i,"") & ">")
			_GUICtrlListBox_AddString($lbDirs, StripTrailCRLF(IniRead($ini,$sect,"Entry" & $i,"")))
		Next
		_GUICtrlListBox_EndUpdate($lbDirs)
	EndIf
EndFunc

;Kopiere Datei
Func CopyFile($socket,byref $status,$fromFname,$toFname)
	Local $recv
	Local $cmd="cp '" & $fromFname & "' '" & $toFname & "'" & $cmdCRLF
	
	$status=""
	$inIO=True
	
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,5000,$status)
	$recv = StripTrailCRLF(StripCmd($cmd,$recv))
	If ($status<>"") Then
		MsgBox(0,"Fehler/Warnung", _
			   StringFormat("Es trat der Fehler %s auf. ",$status) &  _
				@CRLF & "Bei sehr großen Dateien kann dies durch die Kopierdauer bedingt sein und der Kopiervorgang dennoch erfolgreich gewesen sein.",0,$frmMain)
	Else
		If ($recv<>"") Then
			MsgBox(0,"Fehler/Warnung", _
			   StringFormat("Es gab folgende Rückmeldung: %s",$recv),0,$frmMain)
			$status=$recv
		EndIf
	EndIf

   $inIO=False
EndFunc

;Kommando ausführen (mit Fehlercheck)
Func ExecCmdWCheck($socket,byref $status,$cmd,$addtostatusmsg="",$batchmode=false)
	Local $recv
	$status=""
	$inIO=True
	
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,5000,$status)
	$recv = StripTrailCRLF(StripCmd($cmd,$recv))
	If ($status<>"") Then
		If Not $batchmode Then
			MsgBox(0,"Fehler/Warnung",StringFormat("Es trat der Fehler %s auf. ",$status) & $addtostatusmsg,0,$frmMain)
		EndIf
	Else
		If ($recv<>"") Then
			If Not $batchmode Then
				MsgBox(0,"Fehler/Warnung",StringFormat("Es gab folgende Rückmeldung: %s",$recv),0,$frmMain)
			EndIf
			$status="Ausgabe: " & $recv
		EndIf
	EndIf

   $inIO=False
EndFunc

;Verschiebe Datei
Func MoveFile($socket,byref $status,$fromFname,$toFname)
	
	ExecCmdWCheck($socket,$status, _
					"mv '" & $fromFname & "' '" & $toFname & "'" & $cmdCRLF)
EndFunc

;Dateiattribute ändern
Func SetAttr($socket,byref $status,$fname,$newattr)
	ExecCmdWCheck($socket,$status, _ 
					"chmod " & $newattr & " '" & $fname & "'" & $cmdCRLF)
EndFunc


;Erstelle Verzeichnis
Func MakeDir($socket,byref $status,$dirName)
	
	ExecCmdWCheck($socket,$status, _ 
					"mkdir '" & $dirName & "'" & $cmdCRLF)
EndFunc

;Lösche Verzeichnis
Func DelDir($socket,byref $status,$dirName)
	
	ExecCmdWCheck($socket,$status, _ 
					"rmdir '" & $dirName & "'" & $cmdCRLF)
EndFunc


;Lösche Datei
Func DelFile($socket,byref $status,$fname)
	
	ExecCmdWCheck($socket,$status, _ 
					"rm '" & $fname & "'" & $cmdCRLF, _
					@CRLF & "Bei sehr großen Dateien kann dies durch die Löschdauer bedingt sein und der Löschvorgang dennoch erfolgreich gewesen sein.")
EndFunc



Func ListViewChDir()
	If IsDirSelected() Then
		ChDirGui($socket,$status,SelectedFileName())
	EndIf
EndFunc

Func LvMountChDir()
	If IsArray($selMountItem) Then
		ChDirGui($socket,$status,$selMountItem[1])
	EndIf
EndFunc

Func IsDirSelected()
	If isArray($selItem) Then
		;MsgBox(0,"cd", "cd " & $selItem[1])
		Return (StringLeft($selItem[4],1)="d")
	Else
		Return false
	EndIf
EndFunc

Func IsFileSelected()
	If isArray($selItem) Then
		;MsgBox(0,"cd", "cd " & $selItem[1])
		Return ((StringLeft($selItem[4],1)<>"d") And (StringLeft($selItem[4],1)<>"l"))
	Else
		Return false
	EndIf
EndFunc

Func SelectedFileName()
	If isArray($selItem) Then
		;MsgBox(0,"cd", "cd " & $selItem[1])
		Return $selItem[1];
	EndIf
EndFunc

Func SelectedFileSize()
	If IsFileSelected() Then
		;MsgBox(0,"cd", "cd " & $selItem[1])
		Return $selItem[2];
	Else
		Return 0;
	EndIf
EndFunc



;Close-Handler
Func EvtAppClose()
	_Timer_KillAllTimers($frmMain)
	;GUICtrlSetData($lbStatus,"closing")
	TelnetDisconnect($socket)
	TCPShutdown()
	;MsgBox(0,"AppClose","App Close")
	Exit
EndFunc

;Click-Handler fuer Listview
Func WM_NOTIFY($hWnd, $iMsg, $iwParam, $ilParam)
	#forceref $hWnd, $iMsg, $iwParam
	Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $hWndListView, $hWndMount, $hWndLbDirs,$tInfo
	Local $aitem
	$hWndListView = $ListView1
	If Not IsHWnd($hWndListView) Then $hWndListView = GUICtrlGetHandle($hWndListView)

	$hWndMount = $lvMount
	If Not IsHWnd($hWndMount) Then $hWndMount = GUICtrlGetHandle($hWndMount)

	$hWndLbDirs = $lbDirs
	If Not IsHWnd($hWndLbDirs) Then $hWndLbDirs = GUICtrlGetHandle($hWndLbDirs)

	$tNMHDR = DllStructCreate($tagNMHDR, $ilParam)
	$hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom"))
	$iIDFrom = DllStructGetData($tNMHDR, "IDFrom")
	$iCode = DllStructGetData($tNMHDR, "Code")
	Switch $hWndFrom	
		Case $hWndListView
			Switch $iCode
				Case $LVN_ITEMCHANGING ; An item is changing (ITEM_CHANGED ?)
					$tInfo = DllStructCreate($tagNMLISTVIEW, $ilParam)
					$selItem = _GUICtrlListView_GetItemTextArray($ListView1, DllStructGetData($tInfo, "Item"))
					_GUICtrlButton_SetText($pbAddFilename,"<-- " & $selItem[1])
				; NM_RETURN: The control has the input focus and that the user has pressed the ENTER key
				Case $NM_DBLCLK,$NM_RETURN ; Sent by a list-view control when the user double-clicks an item with the left mouse button
					$tInfo = DllStructCreate($tagNMITEMACTIVATE, $ilParam)
					If (StringLeft($selItem[4],1)="d") Then
					 ChDirGui($socket,$status,$selItem[1])
					EndIf
			EndSwitch
		Case $hWndMount
			Switch $iCode
				Case $LVN_ITEMCHANGING ; An item is changing (ITEM_CHANGED ?)
					$tInfo = DllStructCreate($tagNMLISTVIEW, $ilParam)
					$selMountItem = _GUICtrlListView_GetItemTextArray($lvMount, DllStructGetData($tInfo, "Item"))
				Case $NM_DBLCLK ; Sent by a list-view control when the user double-clicks an item with the left mouse button
					$tInfo = DllStructCreate($tagNMITEMACTIVATE, $ilParam)
					 ChDirGui($socket,$status,$selMountItem[1])
			EndSwitch
	EndSwitch
	Return $GUI_RUNDEFMSG
EndFunc   ;==>WM_NOTIFY

;COMMAND-Msg Handler (doubleclick auf Listbox)
Func WM_COMMAND($hWnd, $iMsg, $iwParam, $ilParam)
	#forceref $hWnd, $iMsg
	Local $hWndFrom, $iIDFrom, $iCode, $hWndLbDirs

	$hWndFrom = $ilParam
	$iIDFrom = BitAND($iwParam, 0xFFFF) ; Low Word
	$iCode = BitShift($iwParam, 16) ; Hi Word

	$hWndLbDirs = $lbDirs
	If Not IsHWnd($hWndLbDirs) Then $hWndLbDirs = GUICtrlGetHandle($hWndLbDirs)

	Switch $hWndFrom
		Case $lbDirs, $hWndlbDirs
			Switch $iCode
				Case $LBN_DBLCLK ; Sent when the user double-clicks a string in a list box
				If _GUICtrlListBox_GetCaretIndex($lbDirs)>=0 Then
					ChDirGui($socket,$status,_GUICtrlListBox_GetText($lbDirs,_GUICtrlListBox_GetCaretIndex($lbDirs)))
				EndIf
			EndSwitch
	EndSwitch
	Return $GUI_RUNDEFMSG
EndFunc   ;==>WM_COMMAND

;Telnet-Ausgaben zyklisch darstellen (solange kein Kommando auf Ausgaben wartet)
Func PollTelnet($hWnd, $Msg, $iIDTimer, $dwTime)
	Local $tmpStatus,$recv
   If ($socket<>-1) And (Not $inIO) Then
	  $recv = TCPRecvUntilPrompt($socket,0,$tmpStatus)
   EndIf
EndFunc

;FileSelectFolder ( "dialog text", "root dir" [, flag [, "initial dir" [, hwnd]]] )
;FileOpenDialog ( "title", "init dir", "filter" [, options [, "default name" [, hwnd]]] )
Func DownloadGui($socket,byref $status,$IsAscii)
	If IsFileSelected() Then
		Local $targetfname=FileSaveDialog ( "Datei Download", $lastULDLDir, "Alle Dateien (*.*)" ,16,SelectedFileName(),$frmMain)
		If Not @error Then
			$lastULDLDir=DriveAndDir($targetfname)
			DownloadFileHexdump($socket,$status,SelectedFileName(),SelectedFileSize(),$targetfname,$IsAscii)
		EndIf
	EndIf
EndFunc

;FileOpenDialog ( "title", "init dir", "filter" [, options [, "default name" [, hwnd]]] )
Func UploadGui($socket,byref $status,$IsAscii)
	Local $sourcefname=FileOpenDialog ( "Datei Upload", $lastULDLDir, "Alle Dateien (*.*)" ,16,"",$frmMain)
	Local $dir
	Local $setattr=''
	If Not @error Then
		$lastULDLDir=DriveAndDir($sourcefname)
		If GetFileDirInfo($socket,$status,FNameAndExt($sourcefname),$dir) Then
			If $dir[10]=FNameAndExt($sourcefname) Then
				If MsgBox(3+32,"Datei überschreiben?", _
				   StringFormat("Die Datei %s existiert bereits. Soll sie überschrieben werden?", _
					 FNameAndExt($sourcefname)),0,$frmMain)<>6 Then Return
				$setattr=LsAttrToOct($dir[0])
			EndIf
		EndIf
		If $isAscii And (StringRegExp($sourcefname,"(?i)\.(png|gif|jpg|jpeg|bmp|tar|zip|gz|rar|rpm)$")=1) Then
			If MsgBox(1+48,"Wirklich Ascii?","Achtung, die Dateiendung deutet auf eine binäre Datei hin. Soll diese wirklich als ASCII hochgeladen werden?",0,$frmMain)=2 Then Return
		EndIf
			
		UploadFileEcho($socket,$status,$sourcefname,$IsAscii,$setattr)
		ReadDirectory($socket,$status)
	EndIf
EndFunc

; download: transfer als hexdump
; echo '\xFF\x10'
;awk fehlt eine bibliothek auf dem ms35
;
; cat "textfile.txt" | hexdump -v -e '"xx" /1 "%02X"'
Func DownloadFileHexdump($socket,byref $status,$sourcefname,$sourcesize,$targetfname,$IsAscii)
	Local $recv
	Local $recvsize

	Local $cmd = "cat """ & $sourcefname & """ | hexdump -v -e '/1 ""%02X""'" & $cmdCRLF

   ;MsgBox(0,"Test",$cmd)

	$status=""
	
	$inIO=True
	$noOutput=True
	
	;query time
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,10000,$status);laengerer Timeout
	
	$noOutput=False
	$inIO=False
	
	If $status<>"" Then
		MsgBox(0,"Fehler:",StringFormat("Fehler beim Download: %s",$status),0,$frmMain)
		Return
	EndIf	

	$recv = StripBeforeCRLF($recv)
	
	If (StringInStr($recv,"hexdump",0)<>0) And _
	   ((StringInStr($recv,"no such file",0)<>0) Or (StringInStr($recv,"command not found",0)<>0)) _
		 And (StringLen($recv)<50) Then
		MsgBox(0,"Fehler:","Das Kommando 'hexdump' wird von diesem Gerät nicht unterstützt. Es ist daher kein Download möglich.", _
				  0,$frmMain)
		Return
	EndIf
	
	;MsgBox(0,"Download","<" & $recv & ">")
	
	;Hex -> Binaer wandeln
	Local $data = Binary("0x" & $recv)
	
	If IsBinary($data)>0 Then
		Local $file = FileOpen($targetfname, 2)
		If $file = -1 Then
			MsgBox(0, "Fehler", "Kann Download-Datei nicht speichern.",0,$frmMain)
		Else
			If ($IsAscii) Then
				$data=BinaryToString($data)
				$recvsize=StringLen($data)
				;LF -> CRLF (aber nur, wenn kein CR voransteht)
				$data=StringRegExpReplace($data, '(^|[^\r])\n', '$1' & $cmdCRLF)
				;2x, da das Pattern je 2 Zeichen erfaßt und daher folgende lfs nicht ersetzt
				$data=StringRegExpReplace($data, '(^|[^\r])\n', '$1' & $cmdCRLF)
			EndIf
			FileWrite($file, $data)
			FileClose($file)
			If Not $isAscii Then $recvSize=FileGetSize($targetfname)

			If $recvsize<>$sourcesize Then
				MsgBox(0,"Warnung", _
				  StringFormat("Warnung: Die Dateigröße der Downloaddatei weicht von der ursprünglichen Größe ab.: %d->%d", _
						$sourcesize,$recvsize),0,$frmMain)
			Else
				MsgBox(0,"OK",StringFormat("Download von %s war erfolgreich.",$targetfname),0,$frmMain)
				$status=""
			EndIf
		EndIf
	Else
	  MsgBox(0,"Downloadfehler","Die Daten vom Hexdump kamen leider nicht in einem verwertbaren Format.",0,$frmMain)
	EndIf
EndFunc

;Gets Path of fname (has trailng BS)
Func DriveAndDir($fname)
   Local $szDrive, $szDir, $szFName, $szExt
   _PathSplit($fname, $szDrive, $szDir, $szFName, $szExt)
	Return $szDrive & $szDir;
EndFunc

;Gets Fname+Ext of path
Func FNameAndExt($fname)
   Local $szDrive, $szDir, $szFName, $szExt
   _PathSplit($fname, $szDrive, $szDir, $szFName, $szExt)
	Return $szFName & $szExt;
EndFunc

; upload: transfer als shell "echo"
; cat | sh >test.txt
; Sicherheitshalber upload in Temp-Datei, danach Groessencheck und rename (mv) auf Zieldatei
; Optimierungsansatz: In mehere "shell scripte aufteilen und mit >> anhängen"
Func UploadFileEcho($socket,byref $status,$sourcefname,$IsAscii,$setattr)
	Local $targetfname
	Local $ascii
	Local $data
	Local $echoline
	Local $count=0
	Local $lastcount=0
	Local $sendworecv=0
	Local $remlen
	Local $strpos
	Local $recv
	Local $dir
	Local $targetsize
	Local $iseof=false
	Local $file
	Local $tmpName="Telnet_Dateimanager.upload"
	
	$targetfname=FNameAndExt($sourcefname);

	Local $cmd = 'cat | sh >"' & $tmpName & '"' & $cmdCRLF

   ;MsgBox(0,"Test",$cmd)

	$status=""
	
	$inIO=True
	$noOutput=True

	;Todo: Test bei Ascii, ob Datei z.B. Ascii 0 enthält -> Fehlermeldung
	If ($isAscii) Then
		$file = FileOpen($sourcefname, 0)
	Else
		$file = FileOpen($sourcefname, 16) ;Binaer erzwingen
	EndIf
	
	If $file=-1 Then 
		MsgBox(0,"Fehler",StringFormat("Fehler beim öffnen von '%s' für Upload.",$sourcefname),0,$frmMain)
		Return
	EndIf
	
	TCPSendEcho ($socket, $cmd)
	
	Sleep(250)
	
	$echoline=""
	
	While Not $iseof
		If (Not $isAscii) Then
			$data=FileRead($file,59) ;0x123.... -> 59 Zeichen geben spaeter grob < 255 Zeichen in der Ausgabe
			$iseof=(@error=-1)
			If @error>0 Then
				MsgBox(0,"Fehler",StringFormat("Fehler beim lesen von '%s' für Upload.",$sourcefname),0,$frmMain)
				ExitLoop
			EndIf
			If Not IsBinary($data) Then ;Manchmal kommt aus FileRead kein Binary heraus, wieso??
				$data=StringToBinary($data)
			EndIf
		Else
			$ascii=FileReadLine($file)
			$iseof=(@error=-1)
			If @error>0 Then
				MsgBox(0,"Fehler",StringFormat("Fehler beim lesen von '%s' für Upload.",$sourcefname),0,$frmMain)
				ExitLoop
			EndIf
			If Not $iseof Then $ascii=$ascii & @LF ;LF anfuegen, wenn zeilen folgen
			$data=StringToBinary($ascii)
		EndIf
		If BinaryLen($data)>0 Then
			$strpos=3
			$remlen=StringLen($data)-$strpos+1
			$recv=""
			While $remlen>0 ;Splitte Zeile ggf. in Stücke a 240 zeichen, Ziel nicht mit langen Zeilen überfordern
				$echoline="echo -e -n '" & StringRegExpReplace(StringMid($data,$strpos,_Min($remlen,120)), '([0-9A-F]{2})', '\\x$1') & "'" & $cmdCRLF
				$strpos=$strpos+_Min($remlen,120)
				$remlen=$remlen-_Min($remlen,120)
				;FileWriteLine('Debug.Txt',$echoline)
				TCPSend ($socket, $echoline)
				$recv=$recv & TCPRecv($socket,1024*16) ;Ausgabe verschlucken
			WEnd
			$count=$count+BinaryLen($data)
			
			If $recv="" Then 
				$sendworecv=$sendworecv+BinaryLen($data)
				;FileWriteLine('Debug.Txt','Count ' & $count & ' Sendworecv ' & $sendworecv)
			Else
				$sendworecv=0
			EndIf
			If $doesecho And ($sendworecv>$maxSendWORecv) Then 
				;FileWriteLine('Debug.Txt','Count ' & $count & ' Sendworecv ' & $sendworecv)
				$sendworecv=0
				_GUICtrlStatusBar_SetText($StatusBar, $count & " / Warte", 1)
				Sleep(250) ;Gegenseite muß auch mal zu Wort kommen...
				TCPRecv($socket,1024*16)
			EndIf

			If Int($count/(1024*5))<>Int($lastcount/(1024*5)) Then
				$lastcount=$count
				_GUICtrlStatusBar_SetText($StatusBar, StringFormat("%d Zeichen gesendet",$count), 1)
			EndIf
		EndIf
	WEnd
	_GUICtrlStatusBar_SetText($StatusBar, StringFormat("%d Zeichen gesendet",$count), 1)
	
	FileClose($file)
	
	;Flush Output
	Sleep(500)
	While 1
		$recv=TCPRecv($socket,1024*16)
		If $recv<>"" Then
			Sleep(250)
		Else
			ExitLoop
		EndIf
	WEnd
	
	TCPSendEcho ($socket, Chr(4)) ;Strg+D -> EOF

;$noOutput=False; !!!Debug

	_GUICtrlStatusBar_SetText($StatusBar, "Warte auf Prompt", 1)
	TCPRecvUntilPrompt($socket,20000,$status)
	$noOutput=False
	
	If $status<>"" Then
		$status=StringFormat("'%s' bei warten auf Prompt nach Upload.",$status)
	Else
		;Upload komplett, ab hier Groessencheck und rename
		If GetFileDirInfo($socket,$status,$tmpName,$dir) Then
			If ($dir[10]=$tmpName) Then
				$targetsize=$dir[4]
				If $targetsize<>$count Then
					$status=StringFormat("Fehlerhafte Dateigröße. Zielwert: %d, Tatsächlich: %d",$count,$targetsize)
				Else
					;attribute (chmod)
					If $setattr<>"" Then
						$cmd="chmod " & $setattr & " " & $tmpName & $cmdCRLF
						$recv=StripCmd($cmd,TCPSendEcho ($socket,$cmd))
						If $recv<>"" Then
							$status=StringFormat("Unerwartete Ausgabe '%s' beim Setzen der Attribute der Uploaddatei. (%s)", _
												$recv,$cmd)
						Else
							If $status<>"" Then
								$status=StringFormat("'%s' beim Ausführen von '%s'.",$status,$cmd)
							EndIf
							;Else ok
						EndIf
					EndIf
					;rename (mv)
					If $status="" Then
						$cmd="mv -f " & $tmpName & ' "' & $targetfname & '"' & $cmdCRLF
						$recv=StripCmd($cmd,TCPSendEcho ($socket,$cmd))
						If $recv<>"" Then
							$status=StringFormat("Unerwartete Ausgabe '%s' beim Umbenennen der Uploaddatei. (%s)", _
												$recv,$cmd)
						Else
							If $status<>"" Then
								$status=StringFormat("'%s' beim Ausführen von '%s'.", $status,$cmd)
							EndIf
							;Else ok
						EndIf
					EndIf
				EndIf
			Else
				$status=StringFormat("Fehlerhafte Verzeichnisinformation bei Größencheck nach Upload, Dateiname: '%s'", _ 
									$dir[10])
			EndIf   
		Else
			$status=StringFormat("'%s' beim Warten auf Prompt nach Größencheck (ls).",$status)
		EndIf
	EndIf
	
	$inIO=False

	;ggf. hier datei prüfen (ls ... oder aehnliches)
	If $status<>"" Then
		MsgBox(0,"Fehler",StringFormat("Fehler beim Dateiupload: %s",$status), 0, $frmMain)
	Else
		MsgBox(0,"OK",StringFormat("Upload von %s abgeschlossen.",$targetfname),0,$frmMain)
	EndIf
EndFunc

;directory entry für datei abfragen (aktuelles Verzeichnis)
Func GetFileDirInfo($socket,byref $status,$fname,ByRef $dir)
	Local $cmd='busybox ls -lea ' & $fname & $cmdCRLF
	Local $cmdls="ls -la --time-style=long-iso" & $fname & $cmdCRLF

	If (Not $hasBusybox) Then $cmd=$cmdls ;Nicht busybox-fähig?
	
	TCPSendEcho ($socket,$cmd)
	Local $recv = TCPRecvUntilPrompt($socket,4000,$status)
	If $status="" Then
		;ANSI Color Codes entfernen
		$recv=StringRegExpReplace($recv,'\e\[[^a-zA-z]*[a-zA-z]','')
		
		$recv = StripTrailCRLF(StripCmd($cmd,$recv))
		;MsgBox(0,"","DirInfo recv: '" & $recv & "'")
		
		If $hasLsFmt=-1 Then
		   $dir=StringRegExp($recv,$lsFmt[UBound($lsFmt)-1],3) ;default: lsFmt[0]
		Else
		   $dir=StringRegExp($recv,$lsFmt[$hasLsFmt],3)
		EndIf
;		$dir = StringRegExp($recv,"([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+(.*)\r",3)
		If (@error=0) Then ; And ($dir[10]=$fname)
			Return True
		Else
			$status=StringFormat("Ausgabe von 'ls' nicht auswertbar: '%s'",$recv)
			Return False
		EndIf
	Else
		Return False
	EndIf
EndFunc

;Konvertiert Attribut-Ausgabe von ls (-rwxr-xr-x) in chmod (755)
Func LsAttrToOct($attr)
	Local $ow=0,$gr=0,$ot=0
	If StringMid($attr,2,1)='r' Then $ow+=4
	If StringMid($attr,3,1)='w' Then $ow+=2
	If StringMid($attr,4,1)='x' Then $ow+=1
	If StringMid($attr,5,1)='r' Then $gr+=4
	If StringMid($attr,6,1)='w' Then $gr+=2
	If StringMid($attr,7,1)='x' Then $gr+=1
	If StringMid($attr,8,1)='r' Then $ot+=4
	If StringMid($attr,9,1)='w' Then $ot+=2
	If StringMid($attr,10,1)='x' Then $ot+=1
	;MsgBox(0,'LsAttrToOct',$attr & "-> " & $ow & $gr & $ot)
	
	Return $ow & $gr & $ot
EndFunc


;cd mit GUI Update (Refresh)
Func ChDirGui($socket,byref $status,$newdir)
   ChDir($socket,$status,$newdir)
   If $status="" Then GetPWD($socket,$status)
   If $status="" Then ReadDirectory($socket,$status)
EndFunc

;"nur" cd
Func ChDir($socket,byref $status,$newdir)
	Local $recv
	Local $cmd='cd "' & $newdir & '"' & $cmdCRLF
	
	$status=""
	
	$inIO=True
	
	;query time
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,2000,$status)
	$recv = StripCmd($cmd,$recv)

   $inIO=False
EndFunc

;Aktuelles Verzeichnis
Func GetPWD($socket,byref $status)
	Local $recv
	Local $cmd='pwd' & $cmdCRLF
	
	$status=""
	
	$inIO=True
	
	;query time
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,2000,$status)
	$recv = StripTrailCRLF(StripCmd($cmd,$recv))
	
   GUICtrlSetData($lbDir,$recv) ;Strip crlf?

   $inIO=False
EndFunc

;Verzeichnisinhalt in listview packen
Func ReadDirectory($socket,byref $status)
   Local $recv,$arr,$i,$lst,$cnt
   ;Local $cmd='busybox ls -le --color=never' & @CRLF
   ;Color Escape codes später filtern (manche busybox ls unterstuetzen kein --color)
   Local $cmd='busybox ls -lea' & $cmdCRLF
   Local $cmdls="ls -la --time-style=long-iso" & $cmdCRLF
   Local $dir

   If (Not $hasBusybox) Then $cmd=$cmdls ;Nicht busybox-fähig?

   $status=""
   $selItem=0 ;globales select item leeren

   $inIO=True

   ;query time
   
   TCPSendEcho ($socket, $cmd)
   $recv = TCPRecvUntilPrompt($socket,5000,$status)   
   $recv = StripCmd($cmd,$recv)
   
   ;Im Fehlerfall nochmal ohne busybox probieren
   If (StringInStr($recv,"command not found")<>0) And (StringInStr($recv,"busybox")<>0) Then
	  $hasBusybox=False;
	  $hasLsFmt=1 ;Format festlegen (hoffentlich)
	  TCPSendEcho ($socket, $cmdls)
	  $recv = TCPRecvUntilPrompt($socket,5000,$status)   
	  $recv = StripCmd($cmd,$recv)
   EndIf
   
   
   ;MsgBox(0,"pbRefresh",$socket & "/" & $recv & "/" & $status)   

   If $status="" Then
	  $recv=StringRegExpReplace($recv,'\e\[[^a-zA-z]*[a-zA-z]','')

	  ;FileWriteLine("Debug.Txt","Dir recv: '" & $recv & "'")

	  If StringInStr($recv,@CRLF)<>0 Then
		 $arr=StringSplit($recv,@CRLF,1)
	  Else
		 $arr=StringSplit($recv,@LF,1)
	  EndIf
	  
	  _GUICtrlListView_DeleteAllItems(GUICtrlGetHandle($ListView1))
	  $cnt=0
	  
	  ;Format ergründen
	  If ($hasLsFmt=-1) And ($arr[0]>0) Then
		 ;MsgBox(0,"",">"& $arr[1] & "<")
		 For $i=0 To UBound($lsFmt)-1
			$dir = StringRegExp($arr[1],$lsFmt[$i],3)
			;MsgBox(0,"",">" & $cnt & ":" & @error & "<")
			If (@error=0) Then
			   $hasLsFmt=$i
			   ExitLoop
			EndIf
		 Next
		 
		 ;debug lsfmt
;		 If @error=0 Then
;			Local $t=$arr[1] & @CRLF
;			For $i=0 To UBound($dir)-1
;			   $t=$t & $i & ":<" & $dir[$i] & ">" & @CRLF
;			Next
;			MsgBox(0,"<" & $hasLsFmt & ">",$t)
;		 EndIf
	  EndIf
   
	  For $lst=0 To 1
		 For $i=1 To $arr[0]
			If $hasLsFmt=-1 Then
			   $dir=StringRegExp($arr[$i],$lsFmt[UBound($lsFmt)-1],3) ;default: letzter lsFmt Eintrag
			Else
			   $dir=StringRegExp($arr[$i],$lsFmt[$hasLsFmt],3)
			EndIf
			
			If (@error=0) And (UBound($dir)>=11) Then
				If ($dir[10]<>'.') And ((($lst=0) And (StringLeft($dir[0],1)="d")) Or (($lst=1) And (StringLeft($dir[0],1)<>"d"))) Then
				   Local $fname=$dir[10]
				   Local $ico=1
				   
				   If StringInStr($dir[0],'x')<>0 Then $ico=2 ;programm
				   If StringRegExp($fname,"(?i)\.(so[.0-9]*|dll)$",0)=1 Then $ico=5 ;dll/lib
				   If StringRegExp($fname,"(?i)\.(mkv|wmv|vob|avi|mp2|mp4|mpg|mpeg|iso|divx|xvid)$",0)=1 Then $ico=6
				   If StringRegExp($fname,"(?i)\.(mp3|wav|aac|ogg)$",0)=1 Then $ico=7
				   If StringRegExp($fname,"(?i)\.(jpg|jpeg|gif|bmp|tif|png|ico)$",0)=1 Then $ico=8

				   If StringLeft($dir[0],1)="l" Then $ico=9
				   If StringLeft($dir[0],1)="d" Then $ico=3
				   ;$ico=1 ;ordner icon, wieso

				  _GUICtrlListView_AddItem($ListView1, $fname, $ico)
				  If StringLeft($dir[0],1)="d" Then $dir[4]='<DIR>'
				  If StringLeft($dir[0],1)="l" Then $dir[4]='<LINK>'
				  _GUICtrlListView_AddSubItem($ListView1, $cnt, $dir[4], 1)
				  If (($dir[6]<>"") Or ($dir[7]<>"") Or ($dir[8]<>"")) Then
					 _GUICtrlListView_AddSubItem($ListView1, $cnt, $dir[6] & " " & $dir[7] & " " & $dir[9] & " " & $dir[8], 2)
				  Else ;iso format date time
					 _GUICtrlListView_AddSubItem($ListView1, $cnt, $dir[9], 2)
				  EndIf
				  _GUICtrlListView_AddSubItem($ListView1, $cnt, $dir[0], 3)

				  $cnt=$cnt+1
			   EndIf
			EndIf
		 Next
	  Next
   EndIf

   $inIO=False
EndFunc

;Mount / Dateisysteminfo lesen -> lvMount
Func ReadMounts($socket,byref $status)
	Local $recv,$arr,$arr2,$i,$lst,$cnt
	Local $cmd='df' & $cmdCRLF
	Local $cmd2='mount' & $cmdCRLF

	$status=""
	
	$selItem=0 ;globales select item leeren

	$inIO=True

	;query time
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,5000,$status)

	$recv = StripCmd($cmd,$recv)
	;MsgBox(0,"pbRefresh",$socket & "/" & $recv & "/" & $status)

	If $status="" Then
		If StringInStr($recv,@CRLF)<>0 Then
			$arr=StringSplit($recv,@CRLF,1)
		Else
			$arr=StringSplit($recv,@LF,1)
		EndIf
		
		TCPSendEcho ($socket, $cmd2)
		$recv = TCPRecvUntilPrompt($socket,5000,$status)
		$recv = StripCmd($cmd2,$recv)
		If $status="" Then
			If StringInStr($recv,@CRLF)<>0 Then
				$arr2=StringSplit($recv,@CRLF,1)
			Else
				$arr2=StringSplit($recv,@LF,1)
			EndIf
		EndIf
	EndIf
	If $status="" Then
		_GUICtrlListView_DeleteAllItems(GUICtrlGetHandle($lvMount))
		$cnt=0
		;df
		For $i=2 To $arr[0]
		; 0                        1           2         3    4   5
		;Filesystem           1k-blocks      Used Available Use% Mounted on
		;/dev/mtdblock/2          61056      1884     59172   3% /usr/local/etc
			Local $dir = StringRegExp($arr[$i],"([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+([^ ]+)\s+(.*)",3)
			If (@error=0) Then 
				_GUICtrlListView_AddItem($lvMount, $dir[5], $cnt)
				_GUICtrlListView_AddSubItem($lvMount, $cnt, $dir[0], 1) ;fs
				If StringIsInt($dir[1]) Then
					_GUICtrlListView_AddSubItem($lvMount, $cnt, Round($dir[1]/1024), 2)
				EndIf
				_GUICtrlListView_AddSubItem($lvMount, $cnt, "-", 3) ;rw
				_GUICtrlListView_AddSubItem($lvMount, $cnt, $dir[4], 4)
				$cnt=$cnt+1
			EndIf
		Next
		;mount
		For $i=1 To $arr2[0]
			;0                  1                   2     3
			;/dev/mtdblock/2 on /usr/local/etc type yaffs (rw,noatime)
			Local $dir = StringRegExp($arr2[$i],"(.*) on (.*) type ([^ ]+) (.*)",3)
			If (@error=0) Then 
				Local $it=_GUICtrlListView_FindText($lvMount,$dir[1],-1,False,False)
				If $it>=0 Then
					If _GUICtrlListView_GetItemText($lvMount,$it,1)=$dir[0] Then
						_GUICtrlListView_SetItemText($lvMount,$it,$dir[2],1)
						_GUICtrlListView_SetItemText($lvMount,$it,$dir[3],3)
					EndIf
				EndIf
			EndIf
		Next
   EndIf

   $inIO=False
EndFunc


;Dateianzeige: Download danach -> ViewFileDlg
Func ViewFile($socket,byref $status,$fname,$fsize)
	Local $recv
	;ToDo: ggf. Prüfen auf Typ der Datei (binär nicht anzeigen)
	Local $cmd = 'cat "' & $fname & '"' & $cmdCRLF
	
	$status=""
	
	If ($fsize > $limitView) Then
		MsgBox(0,"Datei zu groß","Diese Datei ist für diese Funktion zu groß. " & _
				  StringFormat("(Größe: %d bytes, Limit: %d bytes)",$fsize,$limitView),0,$frmMain)
		Return
	EndIf
	$inIO=True
	
	;query time
	TCPSendEcho ($socket, $cmd)
	$recv = TCPRecvUntilPrompt($socket,3000,$status)
	$recv = StripCmd($cmd,$recv)
	If ($status<>"") Then MsgBox(0,StringFormat("Fehler %s bei Warten auf Abschluß. Die Anzeige ist ggf. unvollständig.",$status),0,$frmMain)
   
   ViewFileDlg($recv)

   $inIO=False
EndFunc

;Datei bearbeiten: Download, Editor Starten, Warten auf Bestätigung ggf. Upload
Func EditFileDlg($socket, ByRef $status, $fname,$fsize)

	Local $tmpFile=@ScriptDir & '\Edit\' & FNameAndExt($fname)
	Local $dir
	Local $setattr=''
	DirCreate(@ScriptDir & "\Edit")

	If GetFileDirInfo($socket,$status,$fname,$dir) Then
		If $dir[10]=$fname Then
			$setattr=LsAttrToOct($dir[0])
		EndIf
	EndIf

	DownloadFileHexdump($socket,$status,$fname,$fsize,$tmpFile,True)
	If $status<>"" Then ;Fehler beim Download
		;MsgBox(0,"---","<" & $status & ">")
		Return
	EndIf
	
	Local $lastUlTime=FileGetTime($tmpFile,0,1)
	
	Local $msg2
	Local $sWndActive = WinGetTitle ("[ACTIVE]", "")
	Local $dlgEdit = GUICreate("Datei editieren", 316, 238, -1, -1, -1,-1,$frmMain)
	Local $GroupBox1 = GUICtrlCreateGroup("", 8, 1, 297, 89)
	GUICtrlCreateLabel("Die Datei wurde als Kopie lokal gespeichert und der Editor geöffnet. Änderungen können per Klick auf [Upload] auch mehrfach hochgeladen werden. [Schließen] beendet den Vorgang.", 10, 16, 293, 72)
	GUICtrlCreateGroup("", -99, -99, 1, 1)
	Local $pbEditUpload = GUICtrlCreateButton("&Upload", 73, 203, 75, 25)
	GUICtrlSetTip(-1, "Geänderte Datei hochladen.")
	Local $pbEditClose = GUICtrlCreateButton("&Schließen", 170, 203, 75, 25)
	GUICtrlSetTip(-1, "Dialog schließen. Änderungen bitte vorher ggf. per [Upload] hochladen.")
	GUICtrlCreateLabel("Bearbeite Datei:", 8, 104, 80, 17)
	Local $lblEditFile = GUICtrlCreateLabel($fname, 8, 128, 304, 17)
	GUICtrlCreateLabel("Lokaler Speicherort:", 8, 152, 99, 17)
	Local $lblLocalFName = GUICtrlCreateLabel($tmpFile, 8, 168, 304, 33)
	GUISetState(@SW_SHOW)

	Local $sWndEdit = WinGetTitle ("[ACTIVE]", "")
	ShellExecute(GUICtrlRead($eEditor),$tmpFile)

	While 1
		$msg2 = GUIGetMsg()
		Select
			Case $msg2 = $pbEditUpload
				UploadFileEcho($socket,$status,$tmpFile,True,$setattr)
				WinActivate ($sWndEdit, "")
				If $status="" Then $lastUlTime=FileGetTime($tmpFile,0,1)
				Case $msg2 = $pbEditClose
				If $lastUlTime<>FileGetTime($tmpFile,0,1) Then
					If MsgBox(1+32+256,"Änderungen wirklich verwerfen?", _
						"Die Datei wurde seit dem letzten Upload geändert." & @CRLF & _
						"[OK] verwirft die letzten Änderungen und schließt den Dialog ohne erneuten Upload." & @CRLF & _
						"[Abbrechen] schließt diesen Dialog noch nicht. Sie können dann [Upload] ausführen." _
							,0,$dlgEdit)=1 Then
						ExitLoop
					EndIf
				Else
					;ggf. tmpfile löschen?
					ExitLoop
				EndIf
			Case Else
			;;;
		EndSelect
	WEnd
	GUIDelete($dlgEdit)
	WinActivate ($sWndActive, "")
EndFunc


Func ViewFileDlg(ByRef $str)
   Local $msg2
   Local $sWndActive = WinGetTitle ("[ACTIVE]", "")
   Local $dlgViewFile = GUICreate("View File", 740, 616, -1, -1, -1,-1,$frmMain)
   Local $pbCloseViewFile = GUICtrlCreateButton("&Close", 336, 584, 75, 25)
   Local $eFile = GUICtrlCreateEdit($str, 4, 7, 729, 561)
   ;GUICtrlSetData(-1, "")
   GUISetState(@SW_SHOW)
   Local $dlgViewFile_AccelTable[1][2] = [["{ESC}", $pbCloseViewFile]]
   GUISetAccelerators($dlgViewFile_AccelTable)
   
   _WinAPI_SetFocus ($eFile)
   
   While 1
	  $msg2 = GUIGetMsg()
	  Select
		 Case $msg2 = $pbCloseViewFile
			ExitLoop
		 Case Else
		 ;;;
	  EndSelect
   WEnd
   GUIDelete($dlgViewFile)
   WinActivate ($sWndActive, "")
EndFunc


;Entfernt (echo)kommando von Stringanfang, CRLF sollte in CMD bereits enthalten sein
Func StripCmd($cmd,$recv)
   If $doesecho AND (StringLeft($recv,StringLen($cmd))=$cmd) Then
	 Return StringRight($recv,StringLen($recv)-StringLen($cmd))
   Else ;Manche Terminals erwarten LF geben aber CRLF zurück
	  Local $cmdRepl=StringReplace($cmd,@LF,@CRLF)
	  If $doesecho AND (StringLeft($recv,StringLen($cmdRepl))=$cmdRepl) Then
		 Return StringRight($recv,StringLen($recv)-StringLen($cmdRepl))
	  Else
		 Return $recv
	  EndIf
   EndIf
EndFunc

;Entfernt (echo)kommando von Stringanfang, Nur CRLF wird als Anhaltspunlkt verwendet
Func StripBeforeCRLF($recv)
   If $doesecho AND (StringInStr($recv,@CRLF)<>0)  Then
	 Return StringRight($recv,StringLen($recv)-StringInStr($recv,@CRLF)-1)
   Else
	 If $doesecho AND (StringInStr($recv,@LF)<>0)  Then
		 Return StringRight($recv,StringLen($recv)-StringInStr($recv,@LF)-1)
	  Else
		 Return $recv
	  EndIf
   EndIf
EndFunc

Func TelnetDisconnect(ByRef $socket)   
	If $socket<>-1 Then
		TCPSend ($socket, 'exit' & $cmdCRLF)

		TCPRecv ($socket, 2048)
	
		TCPCloseSocket($socket)
		_GUICtrlStatusBar_SetText($StatusBar, "Nicht verbunden", 0)
		_GUICtrlStatusBar_SetBkColor($StatusBar,$clr_notconnected);
		_GUICtrlStatusBar_SetText($StatusBar, "", 1)
		$socket=-1
	EndIf
EndFunc

;Gibt True zurück und ersetzt Kommando in recv, wenn gefunden
Func FindIACCmd(ByRef $recv,$cmd,$cmdTxt)
	Local $p=StringInStr($recv,$cmd)
	If $p>0 Then
		;MsgBox(0,"huhu",$cmdTxt)
		$recv=StringReplace($recv,$cmd,$cmdTxt,1)
		Return true
	Else
		Return false
	EndIf
EndFunc

Func TelnetConnect($ip,$user,$pw,byref $status)
	Local $recv
	Local $steps="Connect "
	Local $i
	Local $noLogon=($user="") And ($pw="")
	
	If $socket<>-1 Then TelnetDisconnect($socket)
	
	$inIO=True
	
	$hasBusybox=True ;Defaults
	$hasLsFmt=-1
	$cmdCRLF=@CRLF
	
	$status=""
	$socket = TCPConnect( $ip, 23 )
	;if $socket = -1 then
	;	Local $page=_INetGetSource($ip)
	;	$socket = TCPConnect( $ip, 23 )
	;endif
	
	
	If $socket <> -1 Then
	   $steps=$steps & " Ok"
		Local $currtime,$rx,$tx
		
		;Interessant: IAC WILL TRANSMIT-BINARY, 255,251,0 (WON'T') 255,252,0 DO/DONT 253,254 Escape 255: 255,255
		;warte auf irgendwas
		
		;250,FA=SB  251,FB=WILL   252,FC=WON'T   253,FD = DO  254,FE = DON'T
		
		;Sende IAC Codes als Intro, die die eigenen "Wünsche" mitteilen
		
		;IAC DON'T ECHO
		TCPSend($socket,Chr(255) & Chr(254) & Chr(1))
		;IAC WON'T ECHO
		TCPSend($socket,Chr(255) & Chr(252) & Chr(1))
		;IAC WILL Suppress GA
		TCPSend($socket,Chr(255) & Chr(251) & Chr(3))
		;IAC DO Suppress GA
		TCPSend($socket,Chr(255) & Chr(253) & Chr(3))
		;IAC WILL Window Size
		TCPSend($socket,Chr(255) & Chr(251) & Chr(31))
		;IAC DON'T NEW-ENVIRON
		TCPSend($socket,Chr(255) & Chr(254) & Chr(39))
		
		$recv=""
		$noOutput=True
		;Warte auf IAC Antworten. Beim ":" geht's weiter
		For $i=0 To 200		   
			$recv = $recv & TCPRecvUntilRegExp($socket,"[:#]",10,$status)
			
			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(24),"[IAC DO Terminal type]") Then
				;IAC WON'T Terminal Type
				TCPSend($socket,Chr(255) & Chr(252) & Chr(24))
				;Oder z.B.: 255 250 32 0 "ANSI" 255 240
			EndIf

			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(32),"[IAC DO Terminal speed]") Then
				;IAC WON'T Terminal Speed
				TCPSend($socket,Chr(255) & Chr(252) & Chr(32)) 
				;Oder z.B.: 255 250 32 0 "ANSI" 255 240
			EndIf

			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(35),"[IAC DO X Display Location]") Then
				;IAC WON'T Display Location
				TCPSend($socket,Chr(255) & Chr(252) & Chr(35)) 
			EndIf
			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(39),"[IAC DO New Environment]") Then
			   ;IAC WON'T New Environment
				TCPSend($socket,Chr(255) & Chr(252) & Chr(39)) ;252=FC
			 EndIf
			 
			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(1),"[IAC DO Echo]") Then
				;IAC WON'T ECHO
				TCPSend($socket,Chr(255) & Chr(252) & Chr(1))
			EndIf
			FindIACCmd($recv,Chr(255) & Chr(254) & Chr(1),"[IAC DON'T Echo]")
			
			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(31),"[IAC DO Window Size]") Then
				;IAC SB NAWS 512x50 IAC SE
				TCPSend($socket,Chr(255) & Chr(250) & Chr(31) & Chr(2) & Chr(0) & _ 
						Chr(0) & Chr(50) & Chr(255) & Chr(240))
			EndIf
			If FindIACCmd($recv,Chr(255) & Chr(253) & Chr(33),"[IAC DO Remote Flow Control]") Then
				;IAC WON'T Remote Flow Control
				TCPSend($socket,Chr(255) & Chr(252) & Chr(33))
			 EndIf
			 
			If FindIACCmd($recv,Chr(255) & Chr(251) & Chr(5),"[IAC WILL Status]") Then
			   ;IAC DON'T Status
			   TCPSend($socket,Chr(255) & Chr(254) & Chr(5))
			EndIf

			 
			FindIACCmd($recv,Chr(255) & Chr(254) & Chr(33),"[IAC DON'T Remote Flow Control]")
			
			FindIACCmd($recv,Chr(255) & Chr(251) & Chr(3),"[IAC WILL Suppress GO Ahead]")
			FindIACCmd($recv,Chr(255) & Chr(252) & Chr(3),"[IAC WON'T Suppress GO Ahead]")
			FindIACCmd($recv,Chr(255) & Chr(253) & Chr(3),"[IAC DO Suppress GO Ahead]")
			FindIACCmd($recv,Chr(255) & Chr(254) & Chr(3),"[IAC DON'T Suppress GO Ahead]")
			
			FindIACCmd($recv,Chr(255) & Chr(251) & Chr(1),"[IAC WILL ECHO]")
			FindIACCmd($recv,Chr(255) & Chr(252) & Chr(1),"[IAC WON'T ECHO]")
			
			;FileWriteLine("Debug.Txt","Connect: '" & $recv & "'")
			
			;String nach Verarbeitung auf Prompt prüfen
			If (StringInStr($recv,":")<>0) Then ExitLoop ;Login-Prompt?
			If $noLogon And ((StringInStr($recv,"#")<>0) Or (StringInStr($recv,"$")<>0)) Then ExitLoop ;CMD Prompt?
			;If $status="" Then ExitLoop
		Next
		;MsgBox(0,"huhu",$recv)
		_GUICtrlEdit_AppendText($eTelnet,$recv)
		$noOutput=False

		#cs
		if $status<>"" then
			MsgBox(0,"1.",$recv & "/" & $status,0,$frmMain)
			;Kein Prompt?, mal probehalber einen "." senden
			$status=""
			TCPSendEcho($socket,'.' & @CRLF)
		 EndIf
		#ce

		 $status=""
		 If $user<>"" Then
			$steps=$steps & ", Userprompt "
			If (StringInStr($recv,":")=0) Then
			   ;Wenn bisher kein Prompt (:) kam
			   $recv = TCPRecvUntilRegExp($socket,":",2000,$status)
			EndIf
			If $status="" Then $steps=$steps & " Ok"
			If ($user='""') Or ($user="''") Then $user=""
			TCPSendEcho($socket,$user & @CRLF)
		 EndIf
		 
		 If ($status="") AND ($pw<>"") Then
			$steps=$steps & ", PWprompt "
			$recv = TCPRecvUntilRegExp($socket,":",2000,$status)
			If $status="" Then $steps=$steps & " Ok"
			
			If ($pw='""') Or ($pw="''") Then $pw=""
			If ($pw="*") Then 
				  $pw=InputBox("Kennwort interaktiv:", "Bitte Kennwort angeben (wird nicht gespeichert): ", _
								"","",300,130)
			EndIf

			TCPSendEcho($socket,$pw & @CRLF)
			_GUICtrlEdit_AppendText($eTelnet,"<pw>" & @CRLF)
		 EndIf
			
		 If $status="" Then
			;warte auf prompt (aber nicht zu lang, da prompt leidlich unbestimmt ist)
			;ohne username ist der prompt ggf. auch schon durch
			If $noLogon=True Then
			   $recv = TCPRecvUntilRegExp($socket,"\$|#",200,$status)
			Else
			   $recv = TCPRecvUntilRegExp($socket,"\$|#",4000,$status)
			EndIf
			;FileWriteLine("Debug.Txt","Nach pw: '" & $recv & "'")
			$status="";ignoriere ggf. Fehler

			$steps=$steps & ", Prompt "
			;Setze neues Prompt
			;'export PS1?? (gilt dann fuer alle prompts)'
			;PS1='\u@\H:\w\$ '
			TCPSendEcho($socket,"export PS1='" & $prompt & "'" & @CRLF)
			;warte auf neues prompt (muss klappen)
			$recv = TCPRecvUntilPrompt($socket,2000,$status)
			If $status="" Then 
			   $steps=$steps & " Ok"
			   ;antwort enthaelt befehl -> gegenseite schickt echo
			   $doesecho = (StringInStr($recv,"export PS1=")>0)
			   ;wenn noch ein Prompt in Rückgabe ist, dann ist wohl nur ein LF noetig
			   
			   ;FileWriteLine("Debug.Txt","Prompt: Right'" & StringRight($recv,StringLen($prompt)) & "'")

			   If StringRight(StripTrailCRLF($recv),StringLen($prompt))=$prompt _
				  Then $cmdCRLF=@LF
			EndIf
		EndIf
	 Else
		$status="Fehler, IP-Adresse korrekt?"
	 EndIf
	 
	 
	 if $status<>"" then
		 ;Falsche Daten nach connect
		$status=$steps & " " & $status
		TCPCloseSocket($socket)
		$socket=-1
		
		_GUICtrlStatusBar_SetText($StatusBar, "Nicht verbunden", 0)
		_GUICtrlStatusBar_SetBkColor($StatusBar,$clr_notconnected);
		_GUICtrlStatusBar_SetText($StatusBar, "Fehler: " & $status, 1)
	 Else
		 _GUICtrlStatusBar_SetText($StatusBar, "Verbunden", 0)
		 _GUICtrlStatusBar_SetBkColor($StatusBar,$clr_connected);
		 _GUICtrlStatusBar_SetText($StatusBar, "Connect Ok", 1)
	 endif
	$inIO=False
	return $socket
EndFunc

Func TCPSendEcho($socket,$str)
   If Not $doesecho And Not $noOutput Then
	  _GUICtrlEdit_AppendText($eTelnet,$str)
   EndIf
   TCPSend($socket,$str)
EndFunc

;Globale Variable $prompt
Func TCPRecvUntilPrompt($socket,$timeoutms, byref $status)
	Local $r,$rstr = "", $match, $elapsed = 0
		
	$status=""
	do
	    $r = TCPRecv($socket,128*1024)
		If Not $noOutput Then
			_GUICtrlEdit_AppendText($eTelnet,$r)
		EndIf
		$rstr=$rstr & $r
		;FileWriteLine("Debug.Txt",@MIN & ":" & @SEC & "." & @MSEC & " Until Prompt " & $r)
		if @error<>0 then 
			$status="error " & @error
			return ""
		endif
		
		$match = (StringRight($rstr,StringLen($prompt)) = $prompt)
		If ($timeoutms<>0) And (StringLen($rstr)>0) Then _GUICtrlStatusBar_SetText($StatusBar, StringLen($rstr) & " Zeichen", 1)
		
		if Not $match then
		if $elapsed>=$timeoutms then 
				$status="timeout"
				If $timeoutms<>0 Then _GUICtrlStatusBar_SetText($StatusBar, "Timeout", 1)
				return $rstr ;dennoch inhalt zurueckgeben
			 endif
			If $r="" Then
			   Sleep(10)
			   $elapsed+=10
			Else
			   $elapsed=0
			EndIf
		endif
	until $match
	;FileWriteLine("Debug.Txt","rstr1: " & $rstr)
	$rstr=StringLeft($rstr,StringLen($rstr)-StringLen($prompt))
	;FileWriteLine("Debug.Txt","rstr2: " & $rstr)
	return $rstr
EndFunc

Func TCPRecvUntilRegExp($socket,$regexp, $timeoutms, byref $status)
	Local $r,$rstr = "", $match, $elapsed = 0
		
	$status=""
	do
	    $r = TCPRecv($socket,16384,1)
			;MsgBox(0,"huhu1","Binary: " & $r)
		$r=StringReplace(BinaryToString($r),Chr(0),'\0',1) ;replace chr0 with \0, Force ANSI
		
		If Not $noOutput Then
			_GUICtrlEdit_AppendText($eTelnet,$r)
		EndIf
		$rstr &= $r
		
		if @error<>0 then 
			$status="error " & @error
			return ""
		endif
		
		$match = StringRegExp($rstr,$regexp,0)
		
		If $timeoutms<>0 Then _GUICtrlStatusBar_SetText($StatusBar, StringFormat("%d Zeichen",StringLen($rstr)), 1)
		
		if $match = 0 then
			if $elapsed>=$timeoutms then 
				$status="timeout"
				If $timeoutms<>0 Then _GUICtrlStatusBar_SetText($StatusBar, "Timeout", 1)
				return $rstr
			endif
			If $r="" Then
			   Sleep(50)
			   $elapsed+=50
			Else
			   $elapsed=0
			EndIf
		endif
	until $match
	
	return $rstr
 EndFunc
 
Func _GuiCtrlGetFocus($hGui = "")
    Local $InputID = ControlGetHandle($hGui, "", ControlGetFocus($hGui))
    Return _ControlGetGuiID($InputID)
EndFunc  ;==>_GuiCtrlGetFocus

Func _ControlGetGuiID($hCtrl)
    Local $Result = DllCall("user32.dll", "int", "GetDlgCtrlID", "hwnd", $hCtrl)
    If @error = 0 Then Return $Result[0]
    Return SetError(1, 0, '')
EndFunc  ;==>_ControlGetGuiID

;Grafik mit hilfe eine Data-Url darstellen (Browser-Objekt)
Func CreateCCGifCtrl($x,$y,$w,$h)
   Local $dataurl='data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAA'& _
	  'AFgAAAAfCAMAAABUFvrSAAAAB3RJTUUH2wkdBjAIzl5pDAAAAAlwSFlzAAALEgAACxIB0t1+/AAAAARnQU1BAACxjwv8Y'& _
	  'QUAAABaUExURQgICAAAADk5OZKSkL3Gvc7Ozv///zExMa21rdnZ17W1rW9va0JCQhAQEHl5d5yamhgYGGFcX4iEiLm7t1'& _
	  'JSUu/v78bIw87KxiUhISkpKaeqp+vn5/f39zEpKT5nDSUAAAKwSURBVHjatZaLsqIwDIaNpYEiLdCKFNT3f81N2lIu465'& _
	  'ndE9GB/0lH+mfXjxp+J04ATjniuJ2u40yxUhfioJkV9fVZ8HgxGWiCsGfMvlDcBXAXC5RbRNs0Y1VoeqVbCb+YTJr3luF'& _
	  'wUVwQXSrP52IRUczBKU0xjSUJmLWDxQCkw+jVFeutbfO2Z7rvtIQohv1rOGqkILu0SGr/YHCYPKBudoOGINug+lGbjC5n'& _
	  'qAnDYB/gImToiL6g3Ifx3tWCMz+ErdUmGMoqeZkhom1BDBegTw0ULbE7bS5Z4XumT2FS0oAk7/EHRD3ZBHNmGDzRMXlTD'& _
	  'D58wWshTkrCkd/7o33IioRrDrQEncxaOhUKBka/t5DGD42QDnUJSrO3NWq4KP1lnzwz6gweJQWwOIhWtLYZQcGgxPRC8M'& _
	  'YUkZDglGr8vB+Ipu9vweFwVI2oMkId20aGy+CEjQ0wYvXYGKYp/e9y0o9uSNYaR6mCzO4qcKl58FrFcAvrKAPjxYVd+u8'& _
	  'KG4mN6mBqxVSUaMQS/DK+bak6VH5NngRTE7NiwXnVmHvn08ws+kWpfXe2okyc/MY7DjTRkCy2yUwTaUVvEwuGrTttHhsF'& _
	  'csDuDzW6fYG7DYLxGwXiO0PipxnlZWdFYP0lqzgy2qF+3hJp+alruXmmdQ852baYMrelOuW075XwnSjp2CeblUTLujjdA'& _
	  's752fb5sgrWvx1gXy42eclrfbcdUl/A5btPzahD08nPkyNlLSwys02pOK2ab88peGy3+gHq3l7lubb459rVv3haFLc0hR'& _
	  'xfUB8RyW+EeFwE+7B7EZ7OEzFJie9cENJ33eP2gkRTG5IJZbjX9Dxv/Vh2Ta3j8Ldg5ZnIR7BUFbbPyz1eZdzMGKxAXfa'& _
	  'YQinrJ9FEf9hFWKHfV3x0eOlDy/A/zlOv0X+AwPDS4lNwGlRAAAAAElFTkSuQmCC'

   Local $oShell = ObjCreate("Shell.Explorer.2")
   If IsObj($oShell) Then
	  Local $oShell_ctrl = GUICtrlCreateObj($oShell, $x,$y,$w,$h)
	  $oShell.navigate("about:blank")
	  $oShell.document.write('<body style="border:0;margin:0" scroll="no"><image src="' & $dataurl & '"/></body>')
   EndIf
EndFunc
