• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 // Functions for canonicalizing "mailto:" URLs.
6 
7 #include "url/url_canon.h"
8 #include "url/url_canon_internal.h"
9 #include "url/url_file.h"
10 #include "url/url_parse_internal.h"
11 
12 namespace url {
13 
14 namespace {
15 
16 template <typename CHAR, typename UCHAR>
DoCanonicalizeMailtoURL(const URLComponentSource<CHAR> & source,const Parsed & parsed,CanonOutput * output,Parsed * new_parsed)17 bool DoCanonicalizeMailtoURL(const URLComponentSource<CHAR>& source,
18                              const Parsed& parsed,
19                              CanonOutput* output,
20                              Parsed* new_parsed) {
21   // mailto: only uses {scheme, path, query} -- clear the rest.
22   new_parsed->username = Component();
23   new_parsed->password = Component();
24   new_parsed->host = Component();
25   new_parsed->port = Component();
26   new_parsed->ref = Component();
27 
28   // Scheme (known, so we don't bother running it through the more
29   // complicated scheme canonicalizer).
30   new_parsed->scheme.begin = output->length();
31   output->Append("mailto:", 7);
32   new_parsed->scheme.len = 6;
33 
34   bool success = true;
35 
36   // Path
37   if (parsed.path.is_valid()) {
38     new_parsed->path.begin = output->length();
39 
40     // Copy the path using path URL's more lax escaping rules.
41     // We convert to UTF-8 and escape non-ASCII, but leave all
42     // ASCII characters alone.
43     int end = parsed.path.end();
44     for (int i = parsed.path.begin; i < end; ++i) {
45       UCHAR uch = static_cast<UCHAR>(source.path[i]);
46       if (uch < 0x20 || uch >= 0x80)
47         success &= AppendUTF8EscapedChar(source.path, &i, end, output);
48       else
49         output->push_back(static_cast<char>(uch));
50     }
51 
52     new_parsed->path.len = output->length() - new_parsed->path.begin;
53   } else {
54     // No path at all
55     new_parsed->path.reset();
56   }
57 
58   // Query -- always use the default utf8 charset converter.
59   CanonicalizeQuery(source.query, parsed.query, NULL,
60                     output, &new_parsed->query);
61 
62   return success;
63 }
64 
65 } // namespace
66 
CanonicalizeMailtoURL(const char * spec,int spec_len,const Parsed & parsed,CanonOutput * output,Parsed * new_parsed)67 bool CanonicalizeMailtoURL(const char* spec,
68                            int spec_len,
69                            const Parsed& parsed,
70                            CanonOutput* output,
71                            Parsed* new_parsed) {
72   return DoCanonicalizeMailtoURL<char, unsigned char>(
73       URLComponentSource<char>(spec), parsed, output, new_parsed);
74 }
75 
CanonicalizeMailtoURL(const base::char16 * spec,int spec_len,const Parsed & parsed,CanonOutput * output,Parsed * new_parsed)76 bool CanonicalizeMailtoURL(const base::char16* spec,
77                            int spec_len,
78                            const Parsed& parsed,
79                            CanonOutput* output,
80                            Parsed* new_parsed) {
81   return DoCanonicalizeMailtoURL<base::char16, base::char16>(
82       URLComponentSource<base::char16>(spec), parsed, output, new_parsed);
83 }
84 
ReplaceMailtoURL(const char * base,const Parsed & base_parsed,const Replacements<char> & replacements,CanonOutput * output,Parsed * new_parsed)85 bool ReplaceMailtoURL(const char* base,
86                       const Parsed& base_parsed,
87                       const Replacements<char>& replacements,
88                       CanonOutput* output,
89                       Parsed* new_parsed) {
90   URLComponentSource<char> source(base);
91   Parsed parsed(base_parsed);
92   SetupOverrideComponents(base, replacements, &source, &parsed);
93   return DoCanonicalizeMailtoURL<char, unsigned char>(
94       source, parsed, output, new_parsed);
95 }
96 
ReplaceMailtoURL(const char * base,const Parsed & base_parsed,const Replacements<base::char16> & replacements,CanonOutput * output,Parsed * new_parsed)97 bool ReplaceMailtoURL(const char* base,
98                       const Parsed& base_parsed,
99                       const Replacements<base::char16>& replacements,
100                       CanonOutput* output,
101                       Parsed* new_parsed) {
102   RawCanonOutput<1024> utf8;
103   URLComponentSource<char> source(base);
104   Parsed parsed(base_parsed);
105   SetupUTF16OverrideComponents(base, replacements, &utf8, &source, &parsed);
106   return DoCanonicalizeMailtoURL<char, unsigned char>(
107       source, parsed, output, new_parsed);
108 }
109 
110 }  // namespace url
111