Launchd not able to access Mac OS keychains - macos

I have a python script which I am executing through a shell script for some reason(not important here). In my script I am basically fetching some url content and sending emails to a specific people.I have added the security keychain for that using something like this
security add-generic-password -s SMTP -a USERID -w PASSWORD
When run from the command line I was prompted to give access to the
keychain item for the 'security' command. After granting
access via Keychain Access I can run the script and it no longer
prompts for the retrieval of the password and it does send me emails.
But Cron Job and Launchd doesn't give me the desired output. After googling a bit I found that cronjob doesn't have access to keychains and I need to give the password while running as a cron job if I want it to serve the purpose. I am not very sure about launchd if it has access to keychains or not. It seems to have worked for the below person for Ruby.
https://lists.macosforge.org/pipermail/launchd-dev/2008-August/000363.html
I have same problem as that guy did. When invoked from launchctl I do not get any emails. However if I hardcode the passwords in my code I do get the emails at the specified time. So I am assuming that my problem here is the keychains that launchd is not able to read. Is there a way to grant access of keychains to the launchd?
I have my com.Query.plist file in the $HOME/Library/LaunchAgents directory.

I ran into this today too.
It seems to be not well documented, but if you add the following to your plist your application will be able to see the user keychains when running as a LaunchAgent:
<key>SessionCreate</key>
<true/>
Credit to:
Missing certificates and keys in the keychain while using Jenkins/Hudson as Continuous Integration for iOS and Mac development
https://serverfault.com/questions/328785/how-do-i-launch-a-process-as-a-specific-user-at-startup-on-os-x/

Just for reference
❯ man launchd.plist
...
SessionCreate <boolean>
This key specifies that the job should be spawned into a new security audit session rather than the default session for the context is
belongs to. See auditon(2) for details.
Setting this key will prevent you from accessing the keychain if you're running a LaunchAgent. Just leave the defaults as-is, and keychain access works out of the box—for LaunchAgents.

Related

Windows RDP with AWS EC2 - used to include password, now doesn't

I haven't logged on to my EC2 recently in a few months. Last time I did, it seems like the RDP file that I downloaded had the password in it. That laptop died.
Today, it seems like AWS/EC2 has changed how things work. I'm able to download the RDP file, but it is prompting for a password. When I try to decrypt the password, it wants me to paste or browse to a file on my disk, which I don't have.
Is there a way to re-download my key info? On security then "Key Pairs", I see the key for this server. Can I download that to my disk, or open it somehow?
I see these steps, but they look overwhelming, i.e. I don't have time for that now; I have real work to do:
https://docs.aws.amazon.com/AWSEC2/latest/WindowsGuide/ResettingAdminPassword_EC2Config.html
I was able to create a new key pair, but not sure if I can associate it with the instance.
When I click "Get Password" this screen appears:
UPDATE 1: I did find my .pem file, so I was able to use that to logon.
Had I not found it, what would I do?
UPDATE 1: I did find my .pem file, so I was able to use that to logon. Had I not found it, what would I do?
Not much really! This is by design. AWS doesn't store your encryption key, and this prevents AWS personnel to access your instance. That's why you get such an ominous warning when pem file is generated: this is your one and only opportunity to see it - don't lose it.
That said, there are several however.
If you changed your Windows password in windows, or created a new AMI and launched a new instance from it - the pem file won't really help. You can probably create 2 administrator accounts; so if one forgets their password, you can reset it with another one.
Second - if your EBS is not encrypted, you can detach it, launch another instance, and attach EBS to new instance. You won't get your instance back, but you will get the data from that drive.
Finally, the "overwhelming" steps from the link that you posted. Follow good security posture, and you won't need them. But if you get sloppy, it may become your real work... better than polishing a resume...

macOS requesting permissions for network read+write

I am writing a service/module in Go for a bigger system and I'm having trouble with permissions on macOS. I am hoping anyone here has any experience with this.
This module is using network interfaces in macOS (read+write), and therefore needs admin/root permissions. The module is also in the form of a process which will communicate with parent process through stdio. Since it needs root permissions, I have tried wrapping it in AppleScript: do shell script [...] with administrator privileges, but osascripts does not return the output in real time, instead it returns the stdio output when process has exited. I need the stdio output in real-time, and it is annoying to write the password every time the module is started.
So that leaves me with the question of how I can request permissions for network control in Go. Like the popup you see on some programs "wants to use your microphone", only with network permissions. Is this possible?
If not, how can I solve this issue of needing root permission for a real-time module in macOS?
I found a viable solution; launching the script with sudo -S , and asking the user for root password through my own GUI service. As long as the root password isn't stored anywhere, it should be fine security-wise.

How to create .rdp file on Mac OS that allows auto-login

I'm working on a tool that generates .rdp files and then invokes them using Microsoft RDP Client. This tool is running on Mac OS.
Everything works well, the only problem is that I can't figure out of how I can generate 'password 51:b' field properly. On Windows this can be done easily by using CryptProtectData method from Crypt32.dll library. How can I do the same on Mac.
Another option could be to use "rdp://" URL scheme, but it doesn't seem allow to pass password this way.
So the question is how can I implement auto-login on Mac if I use third-party RDP client.
As far as i know you can't. You can however create a "User Account" and a Server configuration and add both to the client. The connection will then be visible on the main window and you just need to double click it.
To do so, you need to add the password to the Keychain, use /usr/bin/security to do so from a script. It needs to be a generic-password and saved in com.microsoft.rdc.macos. Also be sure to generate an ID according to the RDP Clients scheme, like BFF77777-7777-7777-7777-777777777777.
You may also set the permissions to read that key using /usr/bin/security and set-generic-password-partition-list specifying the right teamid (UBF8T346G9) and again com.microsoft.rdc.macos. You need the admin password to do this step.
Then you can alter the RDP Clients config file, which is a .sqlite file located at /Users/$(whoami)/Library/Containers/com.microsoft.rdc.macos/Data/Library/Application Support/com.microsoft.rdc.macos/com.microsoft.rdc.application-data.sqlite. Add the user configuration in the ZCREDENTIALENTITY table and make sure the ZID matches the one added to the keychain.
To add a server configuration you need to alter the ZBOOKMARKENTITY table. Just add a configuration by hand using the UI and look at the table to get a feeling of how it needs to be setup. Basically you link your user configuration with the server configuratio by making sure that ZCREDENTIAL in ZBOOKMARKENTITY matches Z_PK in ZCREDENTIALENTITY of your user configuration.
I know the answer is a bit late, but it may give you a starting point. This will however not fully automate the process, you will still need to go to the UI and double click the connection you want to use.

hiding passwords in shell scripts

I'm writing a bash script that needs login credentials (username and password) to make an API call. The script will eventually become a cron job, so it's not feasible to prompt the user for login credentials. What is the best way to hide the credentials in a bash script?
If you can't set up restricted read permissions on the bash script itself (e.g. only root can read it), the usual approach is to use a separate file, with said restrictions (only root or a dedicated user can read it (chmod 400 filename)).
This is how you store your ssh keys in ~/.ssh/, as well.
If you are worried about someone having full access to your drive, e.g. someone stealing it, try cryptsetup/luks.
If you are worried about someone reading the unencrypted raw device, you might try breaking up the password, and assemble it in memory when needed...
SSHPASS=$_pass sshpass -e ssh -o StrictHostKeyChecking=no $_host
I use this bit for instance and prompt user input to a restricted file, a bit more security not actually passing the variable during SSH session, but instead defining as an env variable. Haven't had many concerns from my work place Security Engineers. You can always do as others stated and have that file already containing creds rather than prompting and do the same here.

Write to HKEY_LOCAL_MACHINE on Windows 7 without Administrator privilleges

First of all, I realize this is a messy situation, but it's not of my design, and I'm just trying to help, and for that I need your help.
App A is getting installed automatically via SMS installer under the Administrator account, not the PC owner's User account. App A has a registry key defined in HKEY_LOCAL_MACHINE hive.
After App A is installed, we want to edit the above mentioned registry key, to assign the User's C:\Users\USER_ID\Documents\ folder (I'm told we don't don't know who the user is and don't have access to USER_ID during step 1).
I know all about UAC, Application Manifest, and requestedExecutionLevel. However, I'm told we can't expect that all users will be in the Administrators group on their machine.
Solution must be backwards compatible with Windows XP as well.
I'm searching for options to get `C:\Users\USER_ID\Documents\' into the 'HKEY_LOCAL_MACHINE' hive under the above listed conditions.
I found this thread that might be related to a similar situation, but I don't fully understand it yet (so I will give credit to anyone that explain it better):
Find out (read) logged in user in a cmd started as a different user
I also read something that rules out ClickOnce:
Clickonce + HKEY_LOCAL_MACHINE
After App A is installed with admin privileges you are trying to run an additional script as the local user who does not have admin privileges . In order for your secondary script to write to the local machine key it will have to be run with administrative privileges ..period. That said, you have basically two choices:
1) Use the RunAs command to run the script with elevated privileges and have the user type in a admin username and password to run the script with elevated privileges.
2) This is the better way imo - Since SMS is being leveraged as the delivery tool, use its capability to detect and use local client configuration settings to write the key at the time of installation.
So basically the SMS package would have to be setup to run only when the local user logs on one time so that SMS can grab the current user and write it to a file somewhere.. after that is completed SMS can run a separate package as the admin (user will get prompted) to do the software install looking for the file containing the user and then consequently updating the local machine key to the correct user my document path.
Enjoy!

Resources