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 3 // found in the LICENSE file. 4 5 #include "content/browser/renderer_host/pepper/pepper_socket_utils.h" 6 7 #include <string> 8 #include <vector> 9 10 #include "base/logging.h" 11 #include "base/memory/ref_counted.h" 12 #include "base/strings/string_util.h" 13 #include "content/public/browser/browser_thread.h" 14 #include "content/public/browser/content_browser_client.h" 15 #include "content/public/browser/render_frame_host.h" 16 #include "content/public/browser/site_instance.h" 17 #include "content/public/common/content_client.h" 18 #include "net/cert/x509_certificate.h" 19 #include "ppapi/c/private/ppb_net_address_private.h" 20 #include "ppapi/shared_impl/private/net_address_private_impl.h" 21 #include "ppapi/shared_impl/private/ppb_x509_certificate_private_shared.h" 22 23 namespace content { 24 namespace pepper_socket_utils { 25 26 SocketPermissionRequest CreateSocketPermissionRequest( 27 SocketPermissionRequest::OperationType type, 28 const PP_NetAddress_Private& net_addr) { 29 std::string host = 30 ppapi::NetAddressPrivateImpl::DescribeNetAddress(net_addr, false); 31 int port = 0; 32 std::vector<unsigned char> address; 33 ppapi::NetAddressPrivateImpl::NetAddressToIPEndPoint( 34 net_addr, &address, &port); 35 return SocketPermissionRequest(type, host, port); 36 } 37 38 bool CanUseSocketAPIs(bool external_plugin, 39 bool private_api, 40 const SocketPermissionRequest* params, 41 int render_process_id, 42 int render_frame_id) { 43 DCHECK_CURRENTLY_ON(BrowserThread::UI); 44 if (!external_plugin) { 45 // Always allow socket APIs for out-process plugins (other than external 46 // plugins instantiated by the embeeder through 47 // BrowserPpapiHost::CreateExternalPluginProcess). 48 return true; 49 } 50 51 RenderFrameHost* render_frame_host = 52 RenderFrameHost::FromID(render_process_id, render_frame_id); 53 if (!render_frame_host) 54 return false; 55 SiteInstance* site_instance = render_frame_host->GetSiteInstance(); 56 if (!site_instance) 57 return false; 58 if (!GetContentClient()->browser()->AllowPepperSocketAPI( 59 site_instance->GetBrowserContext(), 60 site_instance->GetSiteURL(), 61 private_api, 62 params)) { 63 LOG(ERROR) << "Host " << site_instance->GetSiteURL().host() 64 << " cannot use socket API or destination is not allowed"; 65 return false; 66 } 67 68 return true; 69 } 70 71 bool GetCertificateFields(const net::X509Certificate& cert, 72 ppapi::PPB_X509Certificate_Fields* fields) { 73 const net::CertPrincipal& issuer = cert.issuer(); 74 fields->SetField(PP_X509CERTIFICATE_PRIVATE_ISSUER_COMMON_NAME, 75 new base::StringValue(issuer.common_name)); 76 fields->SetField(PP_X509CERTIFICATE_PRIVATE_ISSUER_LOCALITY_NAME, 77 new base::StringValue(issuer.locality_name)); 78 fields->SetField(PP_X509CERTIFICATE_PRIVATE_ISSUER_STATE_OR_PROVINCE_NAME, 79 new base::StringValue(issuer.state_or_province_name)); 80 fields->SetField(PP_X509CERTIFICATE_PRIVATE_ISSUER_COUNTRY_NAME, 81 new base::StringValue(issuer.country_name)); 82 fields->SetField( 83 PP_X509CERTIFICATE_PRIVATE_ISSUER_ORGANIZATION_NAME, 84 new base::StringValue(JoinString(issuer.organization_names, '\n'))); 85 fields->SetField( 86 PP_X509CERTIFICATE_PRIVATE_ISSUER_ORGANIZATION_UNIT_NAME, 87 new base::StringValue(JoinString(issuer.organization_unit_names, '\n'))); 88 89 const net::CertPrincipal& subject = cert.subject(); 90 fields->SetField(PP_X509CERTIFICATE_PRIVATE_SUBJECT_COMMON_NAME, 91 new base::StringValue(subject.common_name)); 92 fields->SetField(PP_X509CERTIFICATE_PRIVATE_SUBJECT_LOCALITY_NAME, 93 new base::StringValue(subject.locality_name)); 94 fields->SetField(PP_X509CERTIFICATE_PRIVATE_SUBJECT_STATE_OR_PROVINCE_NAME, 95 new base::StringValue(subject.state_or_province_name)); 96 fields->SetField(PP_X509CERTIFICATE_PRIVATE_SUBJECT_COUNTRY_NAME, 97 new base::StringValue(subject.country_name)); 98 fields->SetField( 99 PP_X509CERTIFICATE_PRIVATE_SUBJECT_ORGANIZATION_NAME, 100 new base::StringValue(JoinString(subject.organization_names, '\n'))); 101 fields->SetField( 102 PP_X509CERTIFICATE_PRIVATE_SUBJECT_ORGANIZATION_UNIT_NAME, 103 new base::StringValue(JoinString(subject.organization_unit_names, '\n'))); 104 105 const std::string& serial_number = cert.serial_number(); 106 fields->SetField(PP_X509CERTIFICATE_PRIVATE_SERIAL_NUMBER, 107 base::BinaryValue::CreateWithCopiedBuffer( 108 serial_number.data(), serial_number.length())); 109 fields->SetField(PP_X509CERTIFICATE_PRIVATE_VALIDITY_NOT_BEFORE, 110 new base::FundamentalValue(cert.valid_start().ToDoubleT())); 111 fields->SetField(PP_X509CERTIFICATE_PRIVATE_VALIDITY_NOT_AFTER, 112 new base::FundamentalValue(cert.valid_expiry().ToDoubleT())); 113 std::string der; 114 net::X509Certificate::GetDEREncoded(cert.os_cert_handle(), &der); 115 fields->SetField( 116 PP_X509CERTIFICATE_PRIVATE_RAW, 117 base::BinaryValue::CreateWithCopiedBuffer(der.data(), der.length())); 118 return true; 119 } 120 121 bool GetCertificateFields(const char* der, 122 uint32_t length, 123 ppapi::PPB_X509Certificate_Fields* fields) { 124 scoped_refptr<net::X509Certificate> cert = 125 net::X509Certificate::CreateFromBytes(der, length); 126 if (!cert.get()) 127 return false; 128 return GetCertificateFields(*cert.get(), fields); 129 } 130 131 } // namespace pepper_socket_utils 132 } // namespace content 133