From 5e493c4865110ad117a09fc73831e6eb793db0f5 Mon Sep 17 00:00:00 2001 From: neon443 <69979447+neon443@users.noreply.github.com> Date: Sat, 7 Jun 2025 14:55:29 +0100 Subject: [PATCH] ui to show if conneced, auth and if test succeeded working on requesting and displaying a shell --- ShhShell/SSHHandler.swift | 140 +++++++++++++++++++------------ ShhShell/Views/ContentView.swift | 27 +++++- 2 files changed, 108 insertions(+), 59 deletions(-) diff --git a/ShhShell/SSHHandler.swift b/ShhShell/SSHHandler.swift index 327967a..51a0f86 100644 --- a/ShhShell/SSHHandler.swift +++ b/ShhShell/SSHHandler.swift @@ -52,8 +52,8 @@ class SSHHandler: ObservableObject { func connect() -> Bool { defer { - getHostkey() getAuthMethods() + getHostkey() } var verbosity: Int = 0 @@ -89,9 +89,7 @@ class SSHHandler: ObservableObject { func testExec() -> Bool { if ssh_is_connected(session) == 0 { - if !connect() { return false - } } guard authorized else { return false } @@ -178,58 +176,58 @@ class SSHHandler: ObservableObject { return true } - func authWithKbInt() -> Bool { - var status: CInt - status = ssh_userauth_kbdint(session, nil, nil) - while status == SSH_AUTH_INFO.rawValue { - let name, instruction: String - var nprompts: CInt - - if let namePtr = ssh_userauth_kbdint_getname(session) { - name = String(cString: namePtr) - } else { - return false - } - if let instrPtr = ssh_userauth_kbdint_getinstruction(session) { - instruction = String(cString: instrPtr) - } else { - return false - } - nprompts = ssh_userauth_kbdint_getnprompts(session) - - if name.count > 0 { - print(name) - } - if instruction.count > 0 { - print(instruction) - } - for promptI in 0.. - var echo: CChar = 0 - prompt = ssh_userauth_kbdint_getprompt(session, UInt32(promptI), &echo) - if echo != 0 { - var buffer: [CChar] = Array(repeating: 0, count: 128) - let ptr: UnsafeMutablePointer = .init(mutating: buffer) - print(prompt) - if fgets(&buffer, Int32(MemoryLayout.size(ofValue: buffer)), stdin) == nil { - return false - } - ptr.pointee = 0//prob fucked - if ssh_userauth_kbdint_setanswer(session, UInt32(promptI), buffer) < 0 { - return false - } - memset(&buffer, 0, buffer.count) - } else { - if (ssh_userauth_kbdint_setanswer(session, UInt32(promptI), &password) != 0) { - return false - } - } - } - status = ssh_userauth_kbdint(session, nil, nil) - } - authorized = true - return true - } +// func authWithKbInt() -> Bool { +// var status: CInt +// status = ssh_userauth_kbdint(session, nil, nil) +// while status == SSH_AUTH_INFO.rawValue { +// let name, instruction: String +// var nprompts: CInt +// +// if let namePtr = ssh_userauth_kbdint_getname(session) { +// name = String(cString: namePtr) +// } else { +// return false +// } +// if let instrPtr = ssh_userauth_kbdint_getinstruction(session) { +// instruction = String(cString: instrPtr) +// } else { +// return false +// } +// nprompts = ssh_userauth_kbdint_getnprompts(session) +// +// if name.count > 0 { +// print(name) +// } +// if instruction.count > 0 { +// print(instruction) +// } +// for promptI in 0.. +// var echo: CChar = 0 +// prompt = ssh_userauth_kbdint_getprompt(session, UInt32(promptI), &echo) +// if echo != 0 { +// var buffer: [CChar] = Array(repeating: 0, count: 128) +// let ptr: UnsafeMutablePointer = .init(mutating: buffer) +// print(prompt) +// if fgets(&buffer, Int32(MemoryLayout.size(ofValue: buffer)), stdin) == nil { +// return false +// } +// ptr.pointee = 0//prob fucked +// if ssh_userauth_kbdint_setanswer(session, UInt32(promptI), buffer) < 0 { +// return false +// } +// memset(&buffer, 0, buffer.count) +// } else { +// if (ssh_userauth_kbdint_setanswer(session, UInt32(promptI), &password) != 0) { +// return false +// } +// } +// } +// status = ssh_userauth_kbdint(session, nil, nil) +// } +// authorized = true +// return true +// } func authWithNone() -> Bool { let status = ssh_userauth_none(session, nil) @@ -245,6 +243,38 @@ class SSHHandler: ObservableObject { method = ssh_userauth_list(session, username) } + func openShell() { + var status: CInt + + let channel = ssh_channel_new(session) + guard let channel = channel else { return } + + status = ssh_channel_open_session(channel) + guard status == SSH_OK else { + ssh_channel_free(channel) + return + } + + interactiveShellSession(channel: channel) + + ssh_channel_close(channel) + ssh_channel_send_eof(channel) + ssh_channel_free(channel) + } + + func interactiveShellSession(channel: ssh_channel) { + var status: CInt + + status = ssh_channel_request_pty(channel) + guard status == SSH_OK else { return } + + status = ssh_channel_change_pty_size(channel, 80, 24) + guard status == SSH_OK else { return } + + status = ssh_channel_request_shell(channel) + guard status == SSH_OK else { return } + } + func logSshGetError() { logger.critical("\(String(cString: ssh_get_error(&self.session)))") } diff --git a/ShhShell/Views/ContentView.swift b/ShhShell/Views/ContentView.swift index 187748e..6ef8ebc 100644 --- a/ShhShell/Views/ContentView.swift +++ b/ShhShell/Views/ContentView.swift @@ -9,9 +9,18 @@ import SwiftUI struct ContentView: View { @ObservedObject var handler: SSHHandler + @State var connected: Bool = false + @State var testSucceded: Bool = false var body: some View { VStack { + Text(connected ? "connected" : "not connected") + .foregroundStyle(connected ? .green : .red) + Text(handler.authorized ? "authorized" : "unauthorized") + .foregroundStyle(handler.authorized ? .green : .red) + if testSucceded { + Image(systemName: "checkmark.circle") + } TextField("address", text: $handler.address) .textFieldStyle(.roundedBorder) TextField( @@ -27,15 +36,25 @@ struct ContentView: View { TextField("password", text: $handler.password) .textFieldStyle(.roundedBorder) - Button("connect & auth") { - handler.connect() + Button("connect") { + if handler.connect() { + withAnimation { connected = true } + } handler.authWithPw() } Button("disconnect") { handler.disconnect() + withAnimation { testSucceded = false } + withAnimation { connected = false} } - Button("testExec") { - handler.testExec() + Button("run a test command") { + withAnimation { + if handler.testExec() { + testSucceded = true + } else { + testSucceded = false + } + } } } }