Using Keytool in a java program? - encryption

I am trying to write a program to generate RSA keys private.der, and public.der in PKCS#8, DER format.
I can do it in OpenSSL manually easily, but I have no idea how to do it in java. I read about Keytool that you can also use manually. But I want to automate the process in a program to generate a unique usable keypair each time the program is ran, and export them to a folder.
Any help would be appreciated.

Key generation works as follows:
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
keyGen.initialize(2048); // Keysize
KeyPair kp = keyGen.genKeyPair():
PrivateKey privKey = kp.getPrivate();
PublicKey pubKey = kp.getPublic();
Then use privKey.getEncoded() and pubKey.getEncoded() to get the encoded versions.

Related

R tools to read/write files between local and remote machines

I want to work on a cluster from my local Rstudio. So far, I'm using the following code to read a file:
to_read <- read.table(
pipe('ssh cluster_A "cat /path_on_cluster/file.txt"'),
h=T)
The autologin on cluster_A works fine as ssh directly gets my ~/.ssh/id_rsa file key.
There's 2 issues:
It doesn't work with fread, so can be quite slow to read
I haven't found a way to write files, only read
I was hoping to use scp as a workaround to these issues with something like that:
library(RCurl)
scp(host = "cluster_A",
path = "/path_on_cluster/file.txt",
keypasswd = NA, user = "user_name", rsa = TRUE,
key = "~/.ssh/id_rsa.pub")
But I can't find a way to make it work, as scp from R runs into some issues ("Protocol "scp" not supported or disabled in libcurl"). I can't find any good answer from a google search.
If anyone has a method to use fread and write.table (or other) between my local machine and a remote cluster, that would be very helpful!

Why X509Certificate2 error reading private key in Windows Server 2016, works on W10

I have created a .pfx certificate, with openssl from a certificate file and a private key, on a Mac
I use it in a .Net Core 2.1 project and I read it with:
var certificate = new X509Certificate2(fileName, password);
Then I use it in a function that signs a JWT token.
In windows 10 it works correctly.
But in Windows Server 2016, the certificate is not read correctly and an error occurs when trying to use it to sign (it reads from disk), if debug the program, when analyzing the PrivateKey property of the certificate, i see that it contains an exception (In Windows 10 contains a value).
And now comes the strangest:
If you import the certificate into the system (It appears correctly in the certificate store with the private key) and export it back to a new pfx file and use this file it works correctly.
Why does this happen, is it a bug in openssl or in windows?
Here information how get the certificate, it is from firebase project service account, here a python code for get .pem and .key, then use openssl for create the pfx
import io
import urllib.request
import json,ssl
#Fix for no SSL Validation
ctx = ssl.create_default_context()
ctx.check_hostname = False
ctx.verify_mode = ssl.CERT_NONE
#Here the filename of service account w/o ext, downloaded from then Firebase project
service_account="service_account"
with open(service_account+".json", encoding='utf-8') as data_file:
data = json.loads(data_file.read())
#read the data must replace the literal \n
private_key=data["private_key"].replace("\\n", "\n")
#print(private_key)
#Get the url for get the cetificate data
client_x509_cert_url=data["client_x509_cert_url"]
with urllib.request.urlopen(client_x509_cert_url, context=ctx) as url:
clientData = json.loads(url.read())
#The private key id for get the certificate
private_key_id=data["private_key_id"]
#read the certificate must replace the the literal \n
certificate=clientData[private_key_id].replace("\\n", "\n")
#save then certificate
with open(service_account+".pem", "w") as pem_file:
pem_file.write(certificate)
#save the key
with open(service_account+".key", "w") as key_file:
key_file.write(private_key)
print("Done.")

How to correctly setup keys with Hadley's secure package

I would like to use Hadley Wickam's secure package from GitHub.
The example usage isn't explicit about how to create keys and where to store them and I'm messing something up (possibly more than one thing).
I installed the package
# install.packages("devtools")
devtools::install_github("s-u/PKI") # needed for bug fixes not currently on CRAN
devtools::install_github("hadley/secure")
set up a vault folder:
dir.create("vault")
Then the next step is to add a user / key:
secure::add_user("hackr", local_key())
and of course if I literally run that last line as-is it says
Error: No key matches id_rsa
Because I don't have a key. So, I used PuttyGen to create a public/private RSA key pair.
I saved them to my desktop and tried putting the full path in the command above:
secure::add_user("hackr", local_key("C:/Users/hackr/Desktop/r_public_key"))
But that didn't work:
Error: No key matches
Then I tried saving the public key in the vault and doing:
secure::add_user("hackr", local_key("r_public_key"))
but I got the same error. Next I tried putting the public key in the working directory (one directory higher than the vault) but got the same error.
Finally, I tried copying the keys to C:\Users\hackr\.ssh but that also led to the same error.
I suspect I need to save the key somewhere special (in Windows I'm not sure where that would be?) and/or I am using the wrong type of key since PuttyGen is for SSH (?).
It looks like local_key is assuming your key is stored in ~/.ssh (which is a reasonable assumption). By default it assumes that the file is named id_rsa.pub so if you've renamed it then you'll need to pass the name into local_key.
I haven't used this package but always remember those wise words "Hack-R view the source"
The issue is that Hadley's local_key() function is assuming your key is stored in ~/.ssh which is where the commands below will place it by default, and name it id_rsa.pub. If you have a different setup, you can change the defaults, or you could simply follow the steps below.
Step 1
Go to https://help.github.com/articles/generating-an-ssh-key/
Read up. It's useful stuff to know.
It will tell you to do this in the console:
ssh-keygen -t rsa -b 4096 -C "your_email#example.com"
Set a passphrase. Remember it.
Then enter this:
ssh-add ~/.ssh/id_rsa
Enter your passphrase.
Step 2
Your secure::add_user("hackr", local_key()) should work now.

check if file is a valid pgp encrypted file

I need to check to see if a file is a valid pgp encrypted file or not. Some pgp files that we get have an extension of pgp and some dont. I need to check to see which of the files are pgp encrypted files and which are not. Please let me know if there is a way to tell.
The only certain way is to attempt decrypting the file (e.g. with gpg) and interpret the error output. Unless you limit input to ascii-armored files, in that case you can check for the armor.
The python-gpgme library is a Pythonic wrapper for GPGME, the library allowing programmatic GnuPG access.
If you have some files that may or may not be GnuPG encrypted:
$ head --bytes=1024k < /dev/urandom > lorem
$ head --bytes=1024k < /dev/urandom | gpg --encrypt --recipient DEADBEEF > ipsum
With the gpgme module you can attempt to decrypt the files:
import gpgme
import io
context = gpgme.Context()
for infile_path in ['lorem', 'ipsum']:
with open(infile_path, 'rb') as infile:
outfile = io.BytesIO()
try:
context.decrypt(infile, outfile)
except gpgme.GpgmeError as exc:
if exc.code == gpgme.ERR_NO_DATA:
print(
"Not a GnuPG-encrypted file: ‘{path}’ ({error})".format(
path=infile.name, error=exc.strerror))
else:
print(
"Error decrypting file: ‘{path}’ ({error})".format(
path=infile.name, error=exc.strerror))
else:
print("Successfully decrypted: ‘{path}’".format(
path=infile.name))
That lets you handle three conditions:
The gpgme.Context.decrypt method fails, and the error code is gpgme.ERR_NO_DATA. This means the data stream was not recognised as GnuPG-encrypted data.
The gpgme.Context.decrypt method fails for some other reason. You'll need to decide which other errors you care about here.
The gpgme.Context.decrypt method succeeds. Obviously, the file is a correctly-encrypted file.

Invalid padding error when using decryptBinary

I have a page in my application where users can upload files. When the file has been uploaded I use the encryptBinary function to encrypt the file:
<cffile file="#getTempDirectory()##uploaded.serverFile#"
action="readBinary"
variable="binaryFile">
<cfset encrypted = encryptBinary(binaryFile,application.key,"AES")>
But when I then try to decrypt the file using decryptBinary I get the following error:
An error occurred while trying to encrypt or decrypt your input
string: Invalid padding
The decryption code is (where readFile contains the result of the encryption):
<cfset decrypted = decryptBinary(readFile,application.key,"AES")>
How might I solve this error? Thanks!

Resources