- Apr 04, 2021
-
-
Simon Tatham authored
Now the systray menu includes 'Remove All Keys' and 'Re-encrypt All Keys' options, which do exactly what they say on the tin.
-
Simon Tatham authored
-
- Apr 02, 2021
-
-
Simon Tatham authored
We're no longer calling pageant_nth_ssh*_key or pageant_add_ssh*_key from outside pageant.c. Remove them from pageant.h and turn them static, so that we carry on not doing so.
-
Simon Tatham authored
The GUI loop that responded to the 'Remove Key' button in the key list worked by actually trying to retrieve a pointer to the ssh_key for a stored key, and then passing that back to the delete function. But when a key is encrypted, that pointer is NULL, so we segfaulted. Fixed by changing pageant_delete_ssh2_key() to take a numeric index in the list instead of a key pointer.
-
Simon Tatham authored
Now Windows Pageant has two clearly distinct dialog boxes for requesting a key passphrase: one to use synchronously when the user has just used the 'Add Key' GUI action, and one to use asynchronously in response to an agent client's attempt to use a key that was loaded encrypted. Also fixed the wording in the asynchronous box: there were two copies of the 'enter passphrase' instruction, one from the dialog definition in pageant.rc file and one from the cross-platform pageant.c. Now pageant.c doesn't format a whole user-facing message any more: it leaves that to the platform front end to do it the way it wants. I've also added a call to SetForegroundWindow, to try to get the passphrase prompt into the foreground. In my experience this doesn't actually get it the keyboard focus, which I think is deliberate on Windows's part and there's nothing I can do about it. But at least the user should _see_ that the prompt is there, so they can focus it themself.
-
- Mar 13, 2021
-
-
Simon Tatham authored
The callback-function API in pageant.h for key enumeration is modified so that we pass an array of all the available fingerprints for each key. In Unix Pageant, that's used by the -l option to print whichever fingerprint the user asked for. (Unfortunately, the option name -E is already taken, so for the moment I've called it --fptype. I may revisit that later.) Also, when matching a key by fingerprint, we're prepared to match against any fingerprint type we know, with disambiguating prefixes if necessary (e.g. you can match "md5:ab:12" or "sha256:Ab12". That has to be done a bit carefully, because we match MD5 hex fingerprints case-insensitively, but SHA256 fingerprints are case-sensitive.
-
- Dec 15, 2020
-
-
Simon Tatham authored
The callback function to pageant_enum_keys now takes a flags parameter, which receives the flags word from the extended key list request, if available. (If not, then the flags word is passed as zero.) The only callback that uses this parameter is the one for printing text output from 'pageant -l', which uses it to print a suffix on each line, indicating whether the key is stored encrypted only (so it will need a passphrase on next use), or whether it's stored both encrypted _and_ unencrypted (so that 'pageant -R' will be able to return it to the former state).
-
Simon Tatham authored
This is an extended version of SSH2_AGENTC_REQUEST_IDENTITIES, which augments each entry in the returned key list with an extra field containing additional data about the key. The initial contents of that extra field are a pair of flags indicating whether the key is currently stored in the agent encrypted, decrypted or both. The idea is that this will permit a Pageant-aware client to make decisions based on that. For a start, the output key list can mention it to the user; also, if you try to add a key unencrypted when it's already present, we can discriminate based on whether it's already present _unencrypted_
-
Simon Tatham authored
That's a part of the protocol spec (ish), so it should be somewhere reasonably sensible rather than buried in the middle of a source file.
-
- Feb 15, 2020
-
-
Simon Tatham authored
The reencrypt-all request is unusual in its ability to be _partially_ successful. To handle this I've introduced a new return status, PAGEANT_ACTION_WARNING. At the moment, users of this client code don't expect it to appear on any request, and I'll make them watch for it only in the case where I know a particular function can generate it.
-
Simon Tatham authored
There was a lot of ugly, repetitive, error-prone code that decoded agent responses in raw data buffers. Now my internal client query function is returning something that works as a BinarySource, so we can decode agent responses using the marshal.h system like any other SSH-formatted message in this code base. While I'm at it, I've centralised more of the parsing of key lists (saving repetition in pageant_add_key and pageant_enum_keys), including merging most of the logic between SSH-1 and SSH-2. The old functions pageant_get_keylist1 and pageant_get_keylist2 aren't exposed in pageant.h any more, because they no longer exist in that form, and also because nothing was using them anyway. (Windows Pageant was using the separate pageant_nth_ssh2_key() functions that talk directly to the core, and Unix Pageant was using the more cooked client function pageant_enum_keys.)
-
- Feb 09, 2020
-
-
Simon Tatham authored
This reads data from standard input, turns it into an SSH-2 sign request, and writes the resulting signature blob to standard output. I don't really anticipate many uses for this other than testing. But it _is_ convenient for testing changes to Pageant itself: it lets me ask for a signature without first having to construct a pointless SSH session that will accept the relevant key.
-
- Feb 08, 2020
-
-
Simon Tatham authored
This applies to both server modes ('pageant -E key.ppk [lifetime]') and client mode ('pageant -a -E key.ppk'). I'm not completely confident that the CLI syntax is actually right yet, but for the moment, it's enough that it _exists_. Now I don't have to test the encrypted-key loading via manually mocked-up agent requests.
-
- Feb 02, 2020
-
-
Simon Tatham authored
This begins to head towards the goal of storing a key file encrypted in Pageant, and decrypting it on demand via a GUI prompt the first time a client requests a signature from it. That won't be a facility available in all situations, so we have to be able to return failure from the prompt. More precisely, there are two versions of this API, one in PageantClient and one in PageantListenerClient: the stream implementation of PageantClient implements the former API and hands it off to the latter. Windows Pageant has to directly implement both (but they will end up funnelling to the same function within winpgnt.c). NFC: for the moment, the new API functions are never called, and every implementation of them returns failure.
-
- Jan 26, 2020
-
-
Simon Tatham authored
I've added the gcc-style attribute("printf") to a lot of printf-shaped functions in this code base that didn't have it. To make that easier, I moved the wrapping macro into defs.h, and also enabled it if we detect the __clang__ macro as well as __GNU__ (hence, it will be used when building for Windows using clang-cl). The result is that a great many format strings in the code are now checked by the compiler, where they were previously not. This causes build failures, which I'll fix in the next commit.
-
- Jan 25, 2020
-
-
Simon Tatham authored
This is a pure refactoring: no functional change expected. This commit introduces two new small vtable-style APIs. One is PageantClient, which identifies a particular client of the Pageant 'core' (meaning the code that handles each individual request). This changes pageant_handle_msg into an asynchronous operation: you pass in an agent request message and an identifier, and at some later point, the got_response method in your PageantClient will be called with the answer (and the same identifier, to allow you to match requests to responses). The trait vtable also contains a logging system. The main importance of PageantClient, and the reason why it has to exist instead of just passing pageant_handle_msg a bare callback function pointer and context parameter, is that it provides robustness if a client stops existing while a request is still pending. You call pageant_unregister_client, and any unfinished requests associated with that client in the Pageant core will be cleaned up, so that you're guaranteed that after the unregister operation, no stray callbacks will happen with a stale pointer to that client. The WM_COPYDATA interface of Windows Pageant is a direct client of this API. The other client is PageantListener, the system that lives in pageant.c and handles stream-based agent connections for both Unix Pageant and the new Windows named-pipe IPC. More specifically, each individual connection to the listening socket is a separate PageantClient, which means that if a socket is closed abruptly or suffers an OS error, that client can be unregistered and any pending requests cancelled without disrupting other connections. Users of PageantListener have a second client vtable they can use, called PageantListenerClient. That contains _only_ logging facilities, and at the moment, only Unix Pageant bothers to use it (and even that only in debugging mode). Finally, internally to the Pageant core, there's a new trait called PageantAsyncOp which describes an agent request in the process of being handled. But at the moment, it has only one trivial implementation, which is handed the full response message already constructed, and on the next toplevel callback, passes it back to the PageantClient.
-
- Jan 04, 2019
-
-
Simon Tatham authored
This is the commit that f3295e0f _should_ have been. Yesterday I just added some typedefs so that I didn't have to wear out my fingers typing 'struct' in new code, but what I ought to have done is to move all the typedefs into defs.h with the rest, and then go through cleaning up the legacy 'struct's all through the existing code. But I was mostly trying to concentrate on getting the test suite finished, so I just did the minimum. Now it's time to come back and do it better.
-
- Nov 03, 2018
-
-
Simon Tatham authored
My normal habit these days, in new code, is to treat int and bool as _almost_ completely separate types. I'm still willing to use C's implicit test for zero on an integer (e.g. 'if (!blob.len)' is fine, no need to spell it out as blob.len != 0), but generally, if a variable is going to be conceptually a boolean, I like to declare it bool and assign to it using 'true' or 'false' rather than 0 or 1. PuTTY is an exception, because it predates the C99 bool, and I've stuck to its existing coding style even when adding new code to it. But it's been annoying me more and more, so now that I've decided C99 bool is an acceptable thing to require from our toolchain in the first place, here's a quite thorough trawl through the source doing 'boolification'. Many variables and function parameters are now typed as bool rather than int; many assignments of 0 or 1 to those variables are now spelled 'true' or 'false'. I managed this thorough conversion with the help of a custom clang plugin that I wrote to trawl the AST and apply heuristics to point out where things might want changing. So I've even managed to do a decent job on parts of the code I haven't looked at in years! To make the plugin's work easier, I pushed platform front ends generally in the direction of using standard 'bool' in preference to platform-specific boolean types like Windows BOOL or GTK's gboolean; I've left the platform booleans in places they _have_ to be for the platform APIs to work right, but variables only used by my own code have been converted wherever I found them. In a few places there are int values that look very like booleans in _most_ of the places they're used, but have a rarely-used third value, or a distinction between different nonzero values that most users don't care about. In these cases, I've _removed_ uses of 'true' and 'false' for the return values, to emphasise that there's something more subtle going on than a simple boolean answer: - the 'multisel' field in dialog.h's list box structure, for which the GTK front end in particular recognises a difference between 1 and 2 but nearly everything else treats as boolean - the 'urgent' parameter to plug_receive, where 1 vs 2 tells you something about the specific location of the urgent pointer, but most clients only care about 0 vs 'something nonzero' - the return value of wc_match, where -1 indicates a syntax error in the wildcard. - the return values from SSH-1 RSA-key loading functions, which use -1 for 'wrong passphrase' and 0 for all other failures (so any caller which already knows it's not loading an _encrypted private_ key can treat them as boolean) - term->esc_query, and the 'query' parameter in toggle_mode in terminal.c, which _usually_ hold 0 for ESC[123h or 1 for ESC[?123h, but can also hold -1 for some other intervening character that we don't support. In a few places there's an integer that I haven't turned into a bool even though it really _can_ only take values 0 or 1 (and, as above, tried to make the call sites consistent in not calling those values true and false), on the grounds that I thought it would make it more confusing to imply that the 0 value was in some sense 'negative' or bad and the 1 positive or good: - the return value of plug_accepting uses the POSIXish convention of 0=success and nonzero=error; I think if I made it bool then I'd also want to reverse its sense, and that's a job for a separate piece of work. - the 'screen' parameter to lineptr() in terminal.c, where 0 and 1 represent the default and alternate screens. There's no obvious reason why one of those should be considered 'true' or 'positive' or 'success' - they're just indices - so I've left it as int. ssh_scp_recv had particularly confusing semantics for its previous int return value: its call sites used '<= 0' to check for error, but it never actually returned a negative number, just 0 or 1. Now the function and its call sites agree that it's a bool. In a couple of places I've renamed variables called 'ret', because I don't like that name any more - it's unclear whether it means the return value (in preparation) for the _containing_ function or the return value received from a subroutine call, and occasionally I've accidentally used the same variable for both and introduced a bug. So where one of those got in my way, I've renamed it to 'toret' or 'retd' (the latter short for 'returned') in line with my usual modern practice, but I haven't done a thorough job of finding all of them. Finally, one amusing side effect of doing this is that I've had to separate quite a few chained assignments. It used to be perfectly fine to write 'a = b = c = TRUE' when a,b,c were int and TRUE was just a the 'true' defined by stdbool.h, that idiom provokes a warning from gcc: 'suggest parentheses around assignment used as truth value'!
-
- Oct 04, 2018
-
-
Simon Tatham authored
All the main backend structures - Ssh, Telnet, Pty, Serial etc - now describe structure types themselves rather than pointers to them. The same goes for the codebase-wide trait types Socket and Plug, and the supporting types SockAddr and Pinger. All those things that were typedefed as pointers are older types; the newer ones have the explicit * at the point of use, because that's what I now seem to be preferring. But whichever one of those is better, inconsistently using a mixture of the two styles is worse, so let's make everything consistent. A few types are still implicitly pointers, such as Bignum and some of the GSSAPI types; generally this is either because they have to be void *, or because they're typedefed differently on different platforms and aren't always pointers at all. Can't be helped. But I've got rid of the main ones, at least.
-
- Jul 09, 2018
-
-
Simon Tatham authored
That's the same value as in the OpenSSH source code, so it should be large enough that anyone needing to sign a larger message will have other problems too.
-
- May 27, 2018
-
-
Simon Tatham authored
Now I've got FROMFIELD, I can rework it so that structures providing an implementation of the Socket or Plug trait no longer have to have the vtable pointer as the very first thing in the structure. In particular, this means that the ProxySocket structure can now directly implement _both_ the Socket and Plug traits, which is always _logically_ how it's worked, but previously it had to be implemented via two separate structs linked to each other.
-
- May 25, 2018
-
-
Simon Tatham authored
This gets rid of yet another huge pile of beating around the bush with length-counting. Also, this time, the BinarySink in question is a little more interesting than just being a strbuf every time: on Windows, where the shared-memory Pageant IPC system imposes a hard limit on the size of message we can return, I've written a custom BinarySink implementation that collects up to that much data and then gives up and sets an overflow flag rather than continue to allocate memory. So the main Pageant code no longer has to worry about checking AGENT_MAX_MSGLEN all the time - and better still, the Unix version of Pageant is no longer _limited_ by AGENT_MAX_MSGLEN in its outgoing messages, i.e. it could store a really extra large number of keys if it needed to. That limitation is now a local feature of Windows Pageant rather than intrinsic to the whole code base. (AGENT_MAX_MSGLEN is still used to check incoming agent messages for sanity, however. Mostly that's because I feel I ought to check them against _some_ limit, and this one seems sensible enough. Incoming agent messages are more bounded anyway - they generally don't hold more than _one_ private key.)
-
Simon Tatham authored
This affects all the functions that generate public and private key and signature blobs of all kinds, plus ssh_ecdhkex_getpublic. Instead of returning a bare block of memory and taking an extra 'int *length' parameter, all these functions now write to a BinarySink, and it's the caller's job to have prepared an appropriate one where they want the output to go (usually a strbuf). The main value of this change is that those blob-generation functions were chock full of ad-hoc length-counting and data marshalling. You have only to look at rsa2_{public,private}_blob, for example, to see the kind of thing I was keen to get rid of!
-
- May 12, 2015
-
-
Simon Tatham authored
-
Simon Tatham authored
I've decided against implementing an option exactly analogous to 'ssh-add -L' (printing the full public key of everything in the agent). Instead, you can identify a specific key to display in full, by any of the same means -d lets you use, and then print it in either of the public key formats we support.
-
Simon Tatham authored
Unlike ssh-add, we can identify the key by its comment or by a prefix of its fingerprint as well as using a public key file on disk. The string given as an argument to -d is interpreted as whichever of those things matches; disambiguating prefixes are available if needed.
-
- May 11, 2015
-
-
Simon Tatham authored
It doesn't look very pretty at the moment, but it lists the keys and gets the fingerprints right.
-
Simon Tatham authored
I've now centralised into pageant.c all the logic about trying to load keys of any type, with no passphrase or with the passphrases used in previous key-loading actions or with a new user-supplied passphrase, whether we're the main Pageant process ourself or are talking to another one as a client. The only part of that code remaining in winpgnt.c is the user interaction via dialog boxes, which of course is the part that will need to be done differently on other platforms.
-
- May 07, 2015
-
-
Simon Tatham authored
I've moved the listening socket setup back to before the lifetime preparations, so in particular we find out that we couldn't bind to the socket _before_ we fork. The only part that really needed to come after lifetime setup was the logging setup, so that's now a separate function called later. Also, the random exit(0)s in silly places like x11_closing have turned into setting a time_to_die flag, so that all clean exits funnel back to the end of main() which at least tries to tidy up a bit afterwards. (Finally, fixed a small bug in testing the return value of waitpid(), which only showed up once we didn't exit(0) after the first wait. Ahem.)
-
- May 06, 2015
-
-
Simon Tatham authored
Now it actually logs all its requests and responses, the fingerprints of keys mentioned in all messages, and so on. I've also added the -v option, which causes Pageant in any mode to direct that logging information to standard error. In --debug mode, however, the logging output goes to standard output instead (because when debugging, that information changes from a side effect to the thing you actually wanted in the first place :-). An internal tweak: the logging functions now take a va_list rather than an actual variadic argument list, so that I can pass it through several functions.
-
- May 05, 2015
-
-
Simon Tatham authored
The exact nature of the Socket is left up to the front end to decide, so that we can use a Unix-domain socket on Unix and a Windows named pipe on Windows. But the logic of how we receive data and what we send in response is all cross-platform.
-
Simon Tatham authored
I'm aiming for windows/winpgnt.c to only contain the parts of Windows Pageant that are actually to do with handling the Windows API, and for all the actual agent logic to be cross-platform. This commit is a start: I've moved every function and internal variable that was easy to move. But it doesn't get all the way there - there's still a lot of logic in add_keyfile() and get_keylist*() that would be good to move out to cross-platform code, but it's harder because that code is currently quite intertwined with details of Windows OS interfacing such as printing message boxes and passphrase prompts and calling back out to agent_query if the Pageant doing that job isn't the primary one.
-