OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include <algorithm> | 5 #include <algorithm> |
6 #include <string> | 6 #include <string> |
7 #include <vector> | 7 #include <vector> |
8 | 8 |
9 #include "base/basictypes.h" | 9 #include "base/basictypes.h" |
10 #include "base/file_path.h" | |
11 #include "base/file_util.h" | |
12 #include "base/json/json_reader.h" | |
13 #include "base/memory/scoped_ptr.h" | |
10 #include "base/time.h" | 14 #include "base/time.h" |
11 #include "base/memory/scoped_ptr.h" | 15 #include "base/values.h" |
12 #include "net/base/address_list.h" | 16 #include "net/base/address_list.h" |
13 #include "net/base/dns_util.h" | 17 #include "net/base/dns_util.h" |
14 #include "net/base/io_buffer.h" | 18 #include "net/base/io_buffer.h" |
15 #include "net/base/ip_endpoint.h" | 19 #include "net/base/ip_endpoint.h" |
16 #include "net/dns/dns_protocol.h" | 20 #include "net/dns/dns_protocol.h" |
17 #include "net/dns/dns_query.h" | 21 #include "net/dns/dns_query.h" |
18 #include "net/dns/dns_response.h" | 22 #include "net/dns/dns_response.h" |
19 | 23 |
20 namespace { | 24 namespace { |
21 | 25 |
22 // TODO(ttuttle): This should read from the file, probably in JSON. | 26 bool FitsUint8(int num) { |
27 return (num >= 0) && (num <= kuint8max); | |
28 } | |
29 | |
30 bool FitsUint16(int num) { | |
31 return (num >= 0) && (num <= kuint16max); | |
32 } | |
33 | |
23 bool ReadTestCase(const char* filename, | 34 bool ReadTestCase(const char* filename, |
24 uint16* id, std::string* qname, uint16* qtype, | 35 uint16* id, std::string* qname, uint16* qtype, |
25 std::vector<char>* resp_buf) { | 36 std::vector<char>* resp_buf) { |
26 static const unsigned char resp_bytes[] = { | 37 FilePath filepath = FilePath::FromUTF8Unsafe(filename); |
27 0x00, 0x00, 0x81, 0x80, 0x00, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, | |
28 0x01, 0x61, 0x00, 0x00, 0x01, 0x00, 0x01, | |
29 0x01, 0x61, 0x00, 0x00, 0x01, 0x00, 0x01, | |
30 0x00, 0x00, 0x00, 0xff, 0x00, 0x04, 0x0a, 0x0a, 0x0a, 0x0a }; | |
31 | 38 |
32 *id = 0x0000; | 39 std::string json; |
33 *qname = "a"; | 40 if (!file_util::ReadFileToString(filepath, &json)) { |
34 *qtype = 0x0001; | 41 LOG(ERROR) << "Couldn't read file " << filename << "."; |
35 resp_buf->assign(resp_bytes, resp_bytes + arraysize(resp_bytes)); | 42 return false; |
43 } | |
44 | |
45 scoped_ptr<Value> value(base::JSONReader::Read(json)); | |
46 if (!value.get()) { | |
47 LOG(ERROR) << "Couldn't parse JSON in " << filename << "."; | |
48 return false; | |
49 } | |
50 | |
51 DictionaryValue* dict; | |
52 if (!value->GetAsDictionary(&dict)) { | |
53 LOG(ERROR) << "Test case is not a dictionary."; | |
54 return false; | |
55 } | |
56 | |
57 int id_int; | |
58 if (!dict->GetInteger("id", &id_int)) { | |
cbentzel
2012/06/06 14:50:56
Nit: You could write a helper function such as
bo
| |
59 LOG(ERROR) << "id is missing or not an integer."; | |
60 return false; | |
61 } | |
62 if (!FitsUint16(id_int)) { | |
63 LOG(ERROR) << "id is out of range."; | |
64 return false; | |
65 } | |
66 *id = static_cast<uint16>(id_int); | |
67 | |
68 if (!dict->GetStringASCII("qname", qname)) { | |
cbentzel
2012/06/06 14:50:56
Should you validate that the qname is well formed?
szym
2012/06/06 14:53:57
If it isn't, the stub will fail in line 140.
| |
69 LOG(ERROR) << "qname is missing or not a string."; | |
70 return false; | |
71 } | |
72 | |
73 int qtype_int; | |
74 if (!dict->GetInteger("qtype", &qtype_int)) { | |
75 LOG(ERROR) << "qtype is missing or not an integer."; | |
76 return false; | |
77 } | |
78 if (!FitsUint16(qtype_int)) { | |
79 LOG(ERROR) << "qtype is out of range."; | |
80 return false; | |
81 } | |
82 *qtype = static_cast<uint16>(qtype_int); | |
83 | |
84 ListValue* resp_list; | |
85 if (!dict->GetList("response", &resp_list)) { | |
86 LOG(ERROR) << "response is missing or not a list."; | |
87 return false; | |
88 } | |
89 | |
90 size_t resp_size = resp_list->GetSize(); | |
91 resp_buf->clear(); | |
92 resp_buf->reserve(resp_size); | |
93 for (size_t i = 0; i < resp_size; i++) { | |
94 int resp_byte_int; | |
95 if ((!resp_list->GetInteger(i, &resp_byte_int))) { | |
96 LOG(ERROR) << "response[" << i << "] is not an integer."; | |
97 return false; | |
98 } | |
99 if (!FitsUint8(resp_byte_int)) { | |
100 LOG(ERROR) << "response[" << i << "] is out of range."; | |
101 return false; | |
102 } | |
103 resp_buf->push_back(static_cast<char>(resp_byte_int)); | |
cbentzel
2012/06/06 14:50:56
Should this be a uint8 vector?
szym
2012/06/06 14:53:57
IOBuffer holds char (which makes me a bit uneasy),
cbentzel
2012/06/06 17:11:18
Let's keep as char. Perhaps we should change IOBuf
| |
104 } | |
105 DCHECK(resp_buf->size() == resp_size); | |
36 | 106 |
37 return true; | 107 return true; |
38 } | 108 } |
39 | 109 |
40 } | 110 } |
41 | 111 |
42 int main(int argc, char** argv) { | 112 int main(int argc, char** argv) { |
43 if (argc != 2) { | 113 if (argc != 2) { |
44 LOG(ERROR) << "Usage: " << argv[0] << " test_case_filename"; | 114 LOG(ERROR) << "Usage: " << argv[0] << " test_case_filename"; |
45 return 1; | 115 return 1; |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
90 | 160 |
91 LOG(INFO) << "Address List:"; | 161 LOG(INFO) << "Address List:"; |
92 for (unsigned int i = 0; i < address_list.size(); i++) { | 162 for (unsigned int i = 0; i < address_list.size(); i++) { |
93 LOG(INFO) << "\t" << address_list[i].ToString(); | 163 LOG(INFO) << "\t" << address_list[i].ToString(); |
94 } | 164 } |
95 LOG(INFO) << "TTL: " << ttl.InSeconds() << " seconds"; | 165 LOG(INFO) << "TTL: " << ttl.InSeconds() << " seconds"; |
96 | 166 |
97 return 0; | 167 return 0; |
98 } | 168 } |
99 | 169 |
OLD | NEW |