Advertisement
Guest User

Untitled

a guest
Aug 22nd, 2017
91
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.28 KB | None | 0 0
  1. ```perl
  2. sub _canonicalize {
  3. my ($uri, $EncodeSlash) = @_;
  4. defined $EncodeSlash ? $UNRESERVED{"/"} = 0 : $UNRESERVED{"/"} = 1;
  5. $uri =~ s/\+/%20/g;
  6. $uri =~ s{\G%(..)|(.)}{
  7. my $c = $1 ? chr(hex($1)) : $2;
  8. $UNRESERVED{$c} ? $c : sprintf "%%%02X", ord($c)
  9. }ge;
  10. $uri =~ s/\+/%20/g;
  11. return $uri;
  12. }
  13. sub _uri_encode {
  14. my ($uri, $EncodeSlash) = @_;
  15. my $unreserved_string = defined $EncodeSlash ? "A-Za-z0-9._~-" : "A-Za-z0-9._~/-";
  16. $uri =~ s{([^$unreserved_string])}{ sprintf '%%%02X',ord($1) }sge;
  17. $uri =~ s/\+/%20/g;
  18. $uri = _canonicalize($uri, $EncodeSlash);
  19. return $uri;
  20.  
  21. }
  22.  
  23. sub _str_to_datetime {
  24. my $date = shift;
  25. if ( $date =~ m/^\d{8}T\d{6}Z$/ ) {
  26. # assume basic ISO 8601, as demanded by AWS
  27. return strptime( '%Y%m%dT%H%M%SZ', $date );
  28. } else {
  29. # assume the format given in the AWS4 test suite
  30. $date =~ s/^.{4}//; # remove weekday, as Amazon's test suite contains internally inconsistent dates
  31. return strptime( '%d %b %Y %H:%M:%S %Z', $date );
  32. }
  33. }
  34.  
  35. sub _canonicalize_headers_aws2 {
  36. my $headers = shift;
  37. my @keys = sort grep /^x-amz-/i, keys %$headers;
  38. my $out = '';
  39. for my $key ( @keys ) {
  40. $out .= lc($key).':'.( $headers->{$key} =~ s{^\s+|\s+$}{}sgr )."\012"
  41. }
  42. return $out;
  43. }
  44. sub _canonicalize_headers_aws4 {
  45. my $hdr = shift;
  46. my ($CanonicalHeaders,@SignedHeaders, %new_hdr);
  47. my @headers = grep(!/user-agent|Accept|x-real-ip|accept-language|connection|INTERNAL_REQUEST_ID/i,
  48. keys %$hdr);
  49. for my $header_name (@headers){
  50. $new_hdr{$header_name} = $hdr->{$header_name};
  51. }
  52. # %new_hdr = %$hdr;
  53. for my $key (sort keys %new_hdr){
  54. $new_hdr{$key} =~ s/[\s\t]+/ /g;
  55. $new_hdr{$key} =~ s/^\s?(.+)\s?$/$1/;
  56.  
  57. $CanonicalHeaders .= "$key:$new_hdr{$key}\n";
  58. push @SignedHeaders, $key;
  59. }
  60. my $headers = join (";",@SignedHeaders);
  61. return $CanonicalHeaders, $headers;
  62. }
  63.  
  64. sub _sort_query_string {
  65. return '' unless length $_[0];
  66. my @params;
  67. for my $param (split /&/, $_[0] ) {
  68. my ( $key, $value ) =
  69. map { tr/+/ /; uri_escape( uri_unescape( $_ ) ) }
  70. split /=/, $param;
  71. push @params, join '=', $key, $value;
  72. }
  73. return join '&', sort @params;
  74. }
  75.  
  76. ```
  77. ```perl
  78. sub sign_request_aws4 {
  79. my ($state, $method, $uri, $hdr, $args) = @_;
  80. $args->{credentials} and $args->{credentials}->access_key or return;
  81.  
  82. my $ak = $args->{credentials}->access_key;
  83. my $params;
  84.  
  85. $params->{cred} = $args->{credentials};
  86. $params->{cred}{region} = "ru-msk" unless defined $params->{cred}{region};
  87. $params->{service} = "s3";
  88. # $hdr->{'x-amz-content-sha256'} //= sha256_hex ($args->{body});
  89. $params->{HashedPlayload} = $hdr->{'x-amz-content-sha256'} if $hdr->{'x-amz-content-sha256'};
  90.  
  91. if ($hdr->{'x-amz-date'}) {
  92. delete $hdr->{date};
  93. $params->{timeStamp} = $hdr->{'x-amz-date'};
  94. $params->{dateStamp} = $params->{timeStamp} =~ s/T\d{6}Z//r;
  95. }
  96. elsif ($hdr->{date}) {
  97. my $dt = _str_to_datetime($hdr->{date});
  98. $params->{timeStamp} = $hdr->{date};
  99. $params->{dateStamp} = $dt->ymd('');
  100. }
  101.  
  102. ($params->{CanonicalHeaders}, $params->{SignedHeaders}) = _canonicalize_headers_aws4($hdr);
  103.  
  104. my $auth = _calculating_signature_aws4($method, $uri, $params);
  105.  
  106. $hdr->{authorization} = "AWS4-HMAC-SHA256 Credential=$ak/$auth->{Scope}, SignedHeaders=$params->{SignedHeaders}, Signature=$auth->{Signature}";
  107.  
  108. $state->{auth_params} = $auth;
  109. return $auth->{s2s};
  110. }
  111. ```
  112. ```perl
  113. my ($method, $uri, $params) = @_;
  114.  
  115. my $CanonicalURI = _canonicalize($uri->path);
  116. my $CanonicalQueryString = _sort_query_string $uri->query;
  117.  
  118. my $CanonicalRequest = join("\n",
  119. $method,
  120. $CanonicalURI,
  121. $CanonicalQueryString,
  122. $params->{CanonicalHeaders},
  123. $params->{SignedHeaders},
  124. $params->{HashedPlayload},
  125. );
  126. # p $CanonicalRequest;
  127. my $Scope = join ("/",
  128. $params->{dateStamp},
  129. $params->{cred}{region},
  130. $params->{service},
  131. "aws4_request",
  132. );
  133. my $s2s = join ("\n",
  134. "AWS4-HMAC-SHA256",
  135. $params->{timeStamp},
  136. $Scope,
  137. sha256_hex($CanonicalRequest)
  138. );
  139. # p $s2s;
  140. my $kSecret = encode('UTF-8', "AWS4".$params->{cred}{secret_key});
  141. my $kDate = hmac_sha256($params->{dateStamp}, $kSecret);
  142. my $kRegion = hmac_sha256($params->{cred}{region}, $kDate);
  143. my $kService = hmac_sha256($params->{service}, $kRegion);
  144. my $kSigning = hmac_sha256("aws4_request", $kService);
  145. my $Signature = hmac_sha256_hex( $s2s, $kSigning);
  146.  
  147. return { CanonicalRequest => $CanonicalRequest, Scope => $Scope, s2s => $s2s, Signature => $Signature };
  148. ```
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement