add certlist package for pre-approved certificates
This commit is contained in:
parent
d19cf49e44
commit
a784d86581
|
|
@ -64,6 +64,20 @@ class images(package):
|
|||
|
||||
config(**configDict)
|
||||
|
||||
class certlist(package):
|
||||
# This package holds any certificates that should be considered
|
||||
# pre-approved by the plugin vendor. If you build and host your
|
||||
# own version of the Panda3D plugin, you can add your own
|
||||
# certificates to this list. The certificates in this package
|
||||
# will be assumed to have been approved by the user when he/she
|
||||
# installed the plugin.
|
||||
|
||||
# They should be PEM-encoded and their filenames must end in the
|
||||
# ".pem" or ".crt" extension, and they should be added with the
|
||||
# extract = True flag so they will be extracted to disk.
|
||||
file('/home/drose/mycertpub.pem', extract = True)
|
||||
|
||||
|
||||
class p3dcert(package):
|
||||
# This special application, used to pop up a dialog to prompt the
|
||||
# user to accept or deny unknown applications, is its own package.
|
||||
|
|
|
|||
|
|
@ -88,6 +88,7 @@ P3DInstance(P3D_request_ready_func *func,
|
|||
_got_wparams = false;
|
||||
_p3d_trusted = false;
|
||||
_xpackage = NULL;
|
||||
_certlist_package = NULL;
|
||||
_p3dcert_package = NULL;
|
||||
|
||||
_fparams.set_tokens(tokens, num_tokens);
|
||||
|
|
@ -102,7 +103,7 @@ P3DInstance(P3D_request_ready_func *func,
|
|||
_allow_python_dev = false;
|
||||
_keep_user_env = (_fparams.lookup_token_int("keep_user_env") != 0);
|
||||
_auto_start = (_fparams.lookup_token_int("auto_start") != 0);
|
||||
_auth_button_approved = false;
|
||||
_auth_button_clicked = false;
|
||||
_failed = false;
|
||||
_session = NULL;
|
||||
_auth_session = NULL;
|
||||
|
|
@ -234,6 +235,11 @@ P3DInstance::
|
|||
_image_package = NULL;
|
||||
}
|
||||
|
||||
if (_certlist_package != NULL) {
|
||||
_certlist_package->remove_instance(this);
|
||||
_certlist_package = NULL;
|
||||
}
|
||||
|
||||
if (_p3dcert_package != NULL) {
|
||||
_p3dcert_package->remove_instance(this);
|
||||
_p3dcert_package = NULL;
|
||||
|
|
@ -539,6 +545,10 @@ set_browser_script_object(P3D_object *browser_script_object) {
|
|||
P3D_OBJECT_DECREF(port);
|
||||
}
|
||||
|
||||
if (_origin_hostname.empty() && _origin_protocol == "file:") {
|
||||
_origin_hostname = "localhost";
|
||||
}
|
||||
|
||||
if (_origin_port.empty()) {
|
||||
// Maybe the actual URL doesn't include the port, in which
|
||||
// case it is implicit.
|
||||
|
|
@ -553,8 +563,11 @@ set_browser_script_object(P3D_object *browser_script_object) {
|
|||
}
|
||||
}
|
||||
|
||||
nout << "origin is " << _origin_protocol << "//" << _origin_hostname
|
||||
<< ":" << _origin_port << "\n";
|
||||
nout << "origin is " << _origin_protocol << "//" << _origin_hostname;
|
||||
if (!_origin_port.empty()) {
|
||||
nout << ":" << _origin_port;
|
||||
}
|
||||
nout << "\n";
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -1244,20 +1257,14 @@ auth_finished_sub_thread() {
|
|||
////////////////////////////////////////////////////////////////////
|
||||
void P3DInstance::
|
||||
auth_finished_main_thread() {
|
||||
// Set this flag to indicate that the user has clicked on the red
|
||||
// "auth" button. This eliminates the need to click on the green
|
||||
// "start" button.
|
||||
_auth_button_clicked = true;
|
||||
|
||||
// After the authorization program has returned, check the signature
|
||||
// again.
|
||||
if (check_p3d_signature()) {
|
||||
// Set this flag to indicate that the user has clicked on the red
|
||||
// "auth" button and successfully approved the application's
|
||||
// certificate. This eliminates the need to click on the green
|
||||
// "start" button.
|
||||
_auth_button_approved = true;
|
||||
mark_p3d_trusted();
|
||||
|
||||
} else {
|
||||
// Still untrusted.
|
||||
mark_p3d_untrusted();
|
||||
}
|
||||
check_p3d_signature();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -1292,11 +1299,7 @@ priv_set_p3d_filename(const string &p3d_filename) {
|
|||
return;
|
||||
}
|
||||
|
||||
if (check_p3d_signature()) {
|
||||
mark_p3d_trusted();
|
||||
} else {
|
||||
mark_p3d_untrusted();
|
||||
}
|
||||
check_p3d_signature();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -1505,18 +1508,21 @@ check_matches_component(const string &orig, const string &match) {
|
|||
// Function: P3DInstance::check_p3d_signature
|
||||
// Access: Private
|
||||
// Description: Checks the signature(s) encoded in the p3d file, and
|
||||
// looks to see if any of them are recognized. Returns
|
||||
// true if the signature is recognized and the file
|
||||
// should be trusted, false otherwise.
|
||||
// looks to see if any of them are recognized.
|
||||
//
|
||||
// If the signature is recognized, calls
|
||||
// mark_p3d_trusted(); otherwise, calls
|
||||
// mark_p3d_untrusted().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool P3DInstance::
|
||||
void P3DInstance::
|
||||
check_p3d_signature() {
|
||||
P3DInstanceManager *inst_mgr = P3DInstanceManager::get_global_ptr();
|
||||
if (inst_mgr->get_trusted_environment()) {
|
||||
// If we're in a trusted environment (e.g. the panda3d command
|
||||
// line, where we've already downloaded the p3d file separately),
|
||||
// then everything is approved.
|
||||
return true;
|
||||
mark_p3d_trusted();
|
||||
return;
|
||||
}
|
||||
|
||||
// See if we've previously approved the certificate--any
|
||||
|
|
@ -1531,12 +1537,33 @@ check_p3d_signature() {
|
|||
// Look up the certificate to see if we've stored a copy in our
|
||||
// certs dir.
|
||||
if (inst_mgr->find_cert(cert)) {
|
||||
return true;
|
||||
mark_p3d_trusted();
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Check the list of pre-approved certificates.
|
||||
if (_certlist_package == NULL) {
|
||||
// We have to go download this package.
|
||||
P3DInstanceManager *inst_mgr = P3DInstanceManager::get_global_ptr();
|
||||
P3DHost *host = inst_mgr->get_host(inst_mgr->get_host_url());
|
||||
_certlist_package = host->get_package("certlist", "");
|
||||
if (_certlist_package != NULL) {
|
||||
_certlist_package->add_instance(this);
|
||||
}
|
||||
|
||||
// When the package finishes downloading, we will come back here.
|
||||
return;
|
||||
}
|
||||
|
||||
if (!_certlist_package->get_ready() && !_certlist_package->get_failed()) {
|
||||
// Wait for it to finish downloading.
|
||||
return;
|
||||
}
|
||||
|
||||
// Couldn't find any approved certificates.
|
||||
return false;
|
||||
mark_p3d_untrusted();
|
||||
return;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -1714,7 +1741,7 @@ scan_app_desc_file(TiXmlDocument *doc) {
|
|||
_matches_script_origin = true;
|
||||
}
|
||||
|
||||
if (_auth_button_approved) {
|
||||
if (_auth_button_clicked) {
|
||||
// But finally, if the user has already clicked through the red
|
||||
// "auth" button, no need to present him/her with another green
|
||||
// "play" button as well.
|
||||
|
|
@ -2279,15 +2306,21 @@ set_button_image(ImageType image_type) {
|
|||
////////////////////////////////////////////////////////////////////
|
||||
void P3DInstance::
|
||||
report_package_info_ready(P3DPackage *package) {
|
||||
if (package == _image_package || package == _p3dcert_package) {
|
||||
// A special case: the image package and the p3dcert package get
|
||||
// immediately downloaded, without waiting for anything else.
|
||||
if (package == _p3dcert_package) {
|
||||
// If we're downloading p3dcert, though, put up a progress bar.
|
||||
if (package == _image_package || package == _certlist_package ||
|
||||
package == _p3dcert_package) {
|
||||
// A special case: these packages get immediately downloaded,
|
||||
// without waiting for anything else.
|
||||
if (package == _certlist_package || package == _p3dcert_package) {
|
||||
// If we're downloading one of the two cert packages, though,
|
||||
// put up a progress bar.
|
||||
make_splash_window();
|
||||
if (_splash_window != NULL) {
|
||||
_splash_window->set_install_progress(0.0);
|
||||
_splash_window->set_install_label("Getting Authorization Dialog");
|
||||
if (package == _certlist_package) {
|
||||
_splash_window->set_install_label("Getting Certificates");
|
||||
} else {
|
||||
_splash_window->set_install_label("Getting Authorization Dialog");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -2503,7 +2536,7 @@ report_package_progress(P3DPackage *package, double progress) {
|
|||
// Ignore this.
|
||||
return;
|
||||
}
|
||||
if (package == _p3dcert_package) {
|
||||
if (package == _certlist_package || package == _p3dcert_package) {
|
||||
// This gets its own progress bar.
|
||||
if (_splash_window != NULL) {
|
||||
_splash_window->set_install_progress(progress);
|
||||
|
|
@ -2591,6 +2624,23 @@ report_package_done(P3DPackage *package, bool success) {
|
|||
return;
|
||||
}
|
||||
|
||||
if (package == _certlist_package) {
|
||||
// Another special case: successfully downloading certlist (or
|
||||
// failing to download it) means we can finish checking the
|
||||
// authenticity of the p3d file.
|
||||
|
||||
// Take down the download progress.
|
||||
if (_splash_window != NULL) {
|
||||
_splash_window->set_install_progress(0.0);
|
||||
_splash_window->set_install_label("");
|
||||
}
|
||||
|
||||
P3DInstanceManager *inst_mgr = P3DInstanceManager::get_global_ptr();
|
||||
inst_mgr->read_certlist(package);
|
||||
check_p3d_signature();
|
||||
return;
|
||||
}
|
||||
|
||||
if (package == _p3dcert_package) {
|
||||
// Another special case: successfully downloading p3dcert means we
|
||||
// can enable the auth button.
|
||||
|
|
|
|||
|
|
@ -165,7 +165,7 @@ private:
|
|||
void separate_components(vector<string> &components, const string &str);
|
||||
bool check_matches_component(const string &orig, const string &match);
|
||||
|
||||
bool check_p3d_signature();
|
||||
void check_p3d_signature();
|
||||
void mark_p3d_untrusted();
|
||||
void mark_p3d_trusted();
|
||||
void scan_app_desc_file(TiXmlDocument *doc);
|
||||
|
|
@ -238,6 +238,10 @@ private:
|
|||
|
||||
bool _p3d_trusted;
|
||||
TiXmlElement *_xpackage;
|
||||
|
||||
// Holds the list of certificates that are pre-approved by the
|
||||
// plugin vendor.
|
||||
P3DPackage *_certlist_package;
|
||||
|
||||
// For downloading the p3dcert authorization program.
|
||||
P3DPackage *_p3dcert_package;
|
||||
|
|
@ -252,7 +256,7 @@ private:
|
|||
bool _allow_python_dev;
|
||||
bool _keep_user_env;
|
||||
bool _auto_start;
|
||||
bool _auth_button_approved;
|
||||
bool _auth_button_clicked;
|
||||
bool _failed;
|
||||
|
||||
P3DSession *_session;
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@
|
|||
#include "p3dUndefinedObject.h"
|
||||
#include "p3dNoneObject.h"
|
||||
#include "p3dBoolObject.h"
|
||||
#include "p3dPackage.h"
|
||||
#include "find_root_dir.h"
|
||||
#include "fileSpec.h"
|
||||
#include "get_tinyxml.h"
|
||||
|
|
@ -873,6 +874,42 @@ find_cert(X509 *cert) {
|
|||
return false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: P3DInstanceManager::read_certlist
|
||||
// Access: Public
|
||||
// Description: Reads the pre-approved certificates in the certlist
|
||||
// package and adds them to the in-memory cache.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void P3DInstanceManager::
|
||||
read_certlist(P3DPackage *package) {
|
||||
nout << "reading certlist in " << package->get_package_dir() << "\n";
|
||||
|
||||
vector<string> contents;
|
||||
scan_directory(package->get_package_dir(), contents);
|
||||
|
||||
vector<string>::iterator si;
|
||||
for (si = contents.begin(); si != contents.end(); ++si) {
|
||||
const string &basename = (*si);
|
||||
if (basename.length() > 4) {
|
||||
string suffix = basename.substr(basename.length() - 4);
|
||||
if (suffix == ".pem" || suffix == ".crt") {
|
||||
string filename = package->get_package_dir() + "/" + basename;
|
||||
X509 *x509 = NULL;
|
||||
FILE *fp = fopen(filename.c_str(), "r");
|
||||
if (fp != NULL) {
|
||||
x509 = PEM_read_X509(fp, NULL, NULL, (void *)"");
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
if (x509 != NULL) {
|
||||
string der2 = cert_to_der(x509);
|
||||
_approved_certs.insert(der2);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: P3DInstanceManager::get_cert_dir
|
||||
// Access: Public
|
||||
|
|
|
|||
|
|
@ -35,6 +35,7 @@ class P3DInstance;
|
|||
class P3DSession;
|
||||
class P3DAuthSession;
|
||||
class P3DHost;
|
||||
class P3DPackage;
|
||||
class FileSpec;
|
||||
class TiXmlElement;
|
||||
|
||||
|
|
@ -120,6 +121,7 @@ public:
|
|||
void release_temp_filename(const string &filename);
|
||||
|
||||
bool find_cert(X509 *cert);
|
||||
void read_certlist(P3DPackage *package);
|
||||
string get_cert_dir(X509 *cert);
|
||||
static string cert_to_der(X509 *cert);
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue