Use more appropriate URL base64 encoding and colon separators
authorChip Black <bytex64@bytex64.net>
Sun, 1 Mar 2015 18:15:06 +0000 (12:15 -0600)
committerChip Black <bytex64@bytex64.net>
Sun, 1 Mar 2015 18:15:06 +0000 (12:15 -0600)
aux/cgi/email.cgi
aux/cgi/recovery.cgi

index 62c717d..2b9215b 100755 (executable)
@@ -1,6 +1,7 @@
 #!/usr/bin/perl
 use CGI::Fast qw/:cgi/;
-use Digest::SHA qw/hmac_sha256_base64/;
+use Digest::SHA qw/hmac_sha256/;
+use MIME::Base64 qw/encode_base64url decode_base64url/;
 use Blerg::Database;
 use URI::Escape;
 use Mail::Message;
@@ -38,32 +39,33 @@ sub generate_email_verify_url {
 
     # generate verification data
     my $expiry = time + 900;
-    my $data = "$username;" . uri_escape($email) . ";$expiry";
+    my $email_b64 = encode_base64url($email);
+    my $data = "$username:$email_b64:$expiry";
         
     # HMAC-SHA256 it
-    my $hmac = hmac_sha256_base64($data, $hmac_key);
+    my $hmac = encode_base64url(hmac_sha256($data, $hmac_key));
 
-    return Blerg::Database::BASEURL . "#/account/email-verify/$data;$hmac";
+    return Blerg::Database::BASEURL . "#/email-verify/$data:$hmac";
 }
 
 sub validate_email_data {
     my ($data) = @_;
     my ($payload, $hmac);
 
-    if ($data =~ /^(.*);([^;]+)$/) {
+    if ($data =~ /^(.*):([^:]+)$/) {
         $payload = $1;
         $hmac = $2;
     } else {
         return undef;
     }
 
-    my $computed_hmac = hmac_sha256_base64($payload, $hmac_key);
+    my $computed_hmac = encode_base64url(hmac_sha256($payload, $hmac_key));
     if ($hmac ne $computed_hmac) {
         return undef;
     }
 
-    my ($username, $email, $expiry) = split(';', $payload);
-    $email = uri_unescape($email);
+    my ($username, $email, $expiry) = split(':', $payload);
+    $email = decode_base64url($email);
     if (time > $expiry) {
         return undef;
     }
index 6d6f3a1..186bf2f 100755 (executable)
@@ -1,6 +1,7 @@
 #!/usr/bin/perl
 use CGI::Fast qw/:cgi/;
-use Digest::SHA qw/hmac_sha256_base64/;
+use Digest::SHA qw/hmac_sha256/;
+use MIME::Base64 qw/encode_base64url/;
 use Blerg::Database;
 use strict;
 use v5.10;
@@ -37,31 +38,31 @@ sub generate_reset_url {
     my $expiry = time + $validity;
     my $counter = Blerg::Database::auth_get_counter($username)
         or return undef;
-    my $data = "$username;$expiry;$counter";
+    my $data = "$username:$expiry:$counter";
         
     # HMAC-SHA256 it
-    my $hmac = hmac_sha256_base64($data, $hmac_key);
+    my $hmac = encode_base64url(hmac_sha256($data, $hmac_key));
 
-    return Blerg::Database::BASEURL . "#/recovery/$data;$hmac";
+    return Blerg::Database::BASEURL . "#/recovery/$data:$hmac";
 }
 
 sub validate_reset_data {
     my ($data) = @_;
     my ($payload, $hmac);
 
-    if ($data =~ /^(.*);([^;]+)$/) {
+    if ($data =~ /^(.*):([^:]+)$/) {
         $payload = $1;
         $hmac = $2;
     } else {
         return undef;
     }
 
-    my $computed_hmac = hmac_sha256_base64($payload, $hmac_key);
+    my $computed_hmac = encode_base64url(hmac_sha256($payload, $hmac_key));
     if ($hmac ne $computed_hmac) {
         return undef;
     }
 
-    my ($username, $expiry, $counter) = split(';', $payload);
+    my ($username, $expiry, $counter) = split(':', $payload);
     if (time > $expiry
         || $counter != Blerg::Database::auth_get_counter($username)) {
         return undef;