]> git.mxchange.org Git - quix0rs-gnu-social.git/commitdiff
Added doc comments on Salmon magicsig-related stuff to help in figuring out what...
authorBrion Vibber <brion@pobox.com>
Wed, 5 Jan 2011 22:05:59 +0000 (14:05 -0800)
committerBrion Vibber <brion@pobox.com>
Wed, 5 Jan 2011 22:05:59 +0000 (14:05 -0800)
plugins/OStatus/classes/Magicsig.php
plugins/OStatus/classes/Ostatus_profile.php
plugins/OStatus/lib/magicenvelope.php
plugins/OStatus/lib/salmon.php

index e057deb144d981611face4b6eb00c8c6d76586a6..31d061e6a0148ab90522db25ce3c5f7857440e73 100644 (file)
@@ -39,11 +39,41 @@ class Magicsig extends Memcached_DataObject
 
     public $__table = 'magicsig';
 
+    /**
+     * Key to user.id/profile.id for the local user whose key we're storing.
+     *
+     * @var int
+     */
     public $user_id;
+
+    /**
+     * Flattened string representation of the key pair; callers should
+     * usually use $this->publicKey and $this->privateKey directly,
+     * which hold live Crypt_RSA key objects.
+     *
+     * @var string
+     */
     public $keypair;
+
+    /**
+     * Crypto algorithm used for this key; currently only RSA-SHA256 is supported.
+     *
+     * @var string
+     */
     public $alg;
 
+    /**
+     * Public RSA key; gets serialized in/out via $this->keypair string.
+     *
+     * @var Crypt_RSA
+     */
     public $publicKey;
+
+    /**
+     * PrivateRSA key; gets serialized in/out via $this->keypair string.
+     *
+     * @var Crypt_RSA
+     */
     public $privateKey;
 
     public function __construct($alg = 'RSA-SHA256')
@@ -51,6 +81,13 @@ class Magicsig extends Memcached_DataObject
         $this->alg = $alg;
     }
 
+    /**
+     * Fetch a Magicsig object from the cache or database on a field match.
+     *
+     * @param string $k
+     * @param mixed $v
+     * @return Magicsig
+     */
     public /*static*/ function staticGet($k, $v=null)
     {
         $obj =  parent::staticGet(__CLASS__, $k, $v);
@@ -103,6 +140,14 @@ class Magicsig extends Memcached_DataObject
         return array(false, false, false);
     }
 
+    /**
+     * Save this keypair into the database.
+     *
+     * Overloads default insert behavior to encode the live key objects
+     * as a flat string for storage.
+     *
+     * @return mixed
+     */
     function insert()
     {
         $this->keypair = $this->toString();
@@ -110,6 +155,14 @@ class Magicsig extends Memcached_DataObject
         return parent::insert();
     }
 
+    /**
+     * Generate a new keypair for a local user and store in the database.
+     *
+     * Warning: this can be very slow on systems without the GMP module.
+     * Runtimes of 20-30 seconds are not unheard-of.
+     *
+     * @param int $user_id id of local user we're creating a key for
+     */
     public function generate($user_id)
     {
         $rsa = new Crypt_RSA();
@@ -128,6 +181,12 @@ class Magicsig extends Memcached_DataObject
         $this->insert();
     }
 
+    /**
+     * Encode the keypair or public key as a string.
+     *
+     * @param boolean $full_pair set to false to leave out the private key.
+     * @return string
+     */
     public function toString($full_pair = true)
     {
         $mod = Magicsig::base64_url_encode($this->publicKey->modulus->toBytes());
@@ -140,6 +199,13 @@ class Magicsig extends Memcached_DataObject
         return 'RSA.' . $mod . '.' . $exp . $private_exp;
     }
 
+    /**
+     * Decode a string representation of an RSA public key or keypair
+     * as a Magicsig object which can be used to sign or verify.
+     *
+     * @param string $text
+     * @return Magicsig
+     */
     public static function fromString($text)
     {
         $magic_sig = new Magicsig();
@@ -168,6 +234,14 @@ class Magicsig extends Memcached_DataObject
         return $magic_sig;
     }
 
+    /**
+     * Fill out $this->privateKey or $this->publicKey with a Crypt_RSA object
+     * representing the give key (as mod/exponent pair).
+     *
+     * @param string $mod base64-encoded
+     * @param string $exp base64-encoded exponent
+     * @param string $type one of 'public' or 'private'
+     */
     public function loadKey($mod, $exp, $type = 'public')
     {
         common_log(LOG_DEBUG, "Adding ".$type." key: (".$mod .', '. $exp .")");
@@ -186,11 +260,22 @@ class Magicsig extends Memcached_DataObject
         }
     }
 
+    /**
+     * Returns the name of the crypto algorithm used for this key.
+     *
+     * @return string
+     */
     public function getName()
     {
         return $this->alg;
     }
 
+    /**
+     * Returns the name of a hash function to use for signing with this key.
+     *
+     * @return string
+     * @fixme is this used? doesn't seem to be called by name.
+     */
     public function getHash()
     {
         switch ($this->alg) {
@@ -200,24 +285,48 @@ class Magicsig extends Memcached_DataObject
         }
     }
 
+    /**
+     * Generate base64-encoded signature for the given byte string
+     * using our private key.
+     *
+     * @param string $bytes as raw byte string
+     * @return string base64-encoded signature
+     */
     public function sign($bytes)
     {
         $sig = $this->privateKey->sign($bytes);
         return Magicsig::base64_url_encode($sig);
     }
 
+    /**
+     *
+     * @param string $signed_bytes as raw byte string
+     * @param string $signature as base64
+     * @return boolean
+     */
     public function verify($signed_bytes, $signature)
     {
         $signature = Magicsig::base64_url_decode($signature);
         return $this->publicKey->verify($signed_bytes, $signature);
     }
 
-
+    /**
+     * URL-encoding-friendly base64 variant encoding.
+     *
+     * @param string $input
+     * @return string
+     */
     public static function base64_url_encode($input)
     {
         return strtr(base64_encode($input), '+/', '-_');
     }
 
+    /**
+     * URL-encoding-friendly base64 variant decoding.
+     *
+     * @param string $input
+     * @return string
+     */
     public static function base64_url_decode($input)
     {
         return base64_decode(strtr($input, '-_', '+/'));
index 9c0f014fc6464cea41cb2c2bbc09c4b1fea73531..06e42187d4c8176954f74587eb55a19469f9cc0a 100644 (file)
@@ -331,6 +331,7 @@ class Ostatus_profile extends Memcached_DataObject
      * an acceptable response from the remote site.
      *
      * @param mixed $entry XML string, Notice, or Activity
+     * @param Profile $actor
      * @return boolean success
      */
     public function notifyActivity($entry, $actor)
index 03e6f7c665426b2ff013ea2c34b18dd2f4b36980..6d3956cb9bea8b7b17d92fbde3269cf4f1200113 100644 (file)
@@ -81,6 +81,14 @@ class MagicEnvelope
     }
 
 
+    /**
+     *
+     * @param <type> $text
+     * @param <type> $mimetype
+     * @param <type> $keypair
+     * @return array: associative array of envelope properties
+     * @fixme it might be easier to work with storing envelope data these in the object instead of passing arrays around
+     */
     public function signMessage($text, $mimetype, $keypair)
     {
         $signature_alg = Magicsig::fromString($keypair);
@@ -95,6 +103,13 @@ class MagicEnvelope
         );
     }
 
+    /**
+     * Create an <me:env> XML representation of the envelope.
+     *
+     * @param array $env associative array with envelope data
+     * @return string representation of XML document
+     * @fixme it might be easier to work with storing envelope data these in the object instead of passing arrays around
+     */
     public function toXML($env) {
         $xs = new XMLStringer();
         $xs->startXML();
@@ -110,6 +125,16 @@ class MagicEnvelope
         return $string;
     }
 
+    /**
+     * Extract the contained XML payload, and insert a copy of the envelope
+     * signature data as an <me:provenance> section.
+     *
+     * @param array $env associative array with envelope data
+     * @return string representation of modified XML document
+     *
+     * @fixme in case of XML parsing errors, this will spew to the error log or output
+     * @fixme it might be easier to work with storing envelope data these in the object instead of passing arrays around
+     */
     public function unfold($env)
     {
         $dom = new DOMDocument();
@@ -136,6 +161,14 @@ class MagicEnvelope
         return $dom->saveXML();
     }
 
+    /**
+     * Find the author URI referenced in the given Atom entry.
+     *
+     * @param string $text string containing Atom entry XML
+     * @return mixed URI string or false if XML parsing fails, or null if no author URI can be found
+     *
+     * @fixme XML parsing failures will spew to error logs/output
+     */
     public function getAuthor($text) {
         $doc = new DOMDocument();
         if (!$doc->loadXML($text)) {
@@ -153,11 +186,30 @@ class MagicEnvelope
         }
     }
 
+    /**
+     * Check if the author in the Atom entry fragment claims to match
+     * the given identifier URI.
+     *
+     * @param string $text string containing Atom entry XML
+     * @param string $signer_uri
+     * @return boolean
+     */
     public function checkAuthor($text, $signer_uri)
     {
         return ($this->getAuthor($text) == $signer_uri);
     }
 
+    /**
+     * Attempt to verify cryptographic signing for parsed envelope data.
+     * Requires network access to retrieve public key referenced by the envelope signer.
+     *
+     * Details of failure conditions are dumped to output log and not exposed to caller.
+     *
+     * @param array $env array representation of magic envelope data, as returned from MagicEnvelope::parse()
+     * @return boolean
+     *
+     * @fixme it might be easier to work with storing envelope data these in the object instead of passing arrays around
+     */
     public function verify($env)
     {
         if ($env['alg'] != 'RSA-SHA256') {
@@ -190,12 +242,32 @@ class MagicEnvelope
         return $verifier->verify($env['data'], $env['sig']);
     }
 
+    /**
+     * Extract envelope data from an XML document containing an <me:env> or <me:provenance> element.
+     *
+     * @param string XML source
+     * @return mixed associative array of envelope data, or false on unrecognized input
+     *
+     * @fixme it might be easier to work with storing envelope data these in the object instead of passing arrays around
+     * @fixme will spew errors to logs or output in case of XML parse errors
+     * @fixme may give fatal errors if some elements are missing or invalid XML
+     * @fixme calling DOMDocument::loadXML statically triggers warnings in strict mode
+     */
     public function parse($text)
     {
         $dom = DOMDocument::loadXML($text);
         return $this->fromDom($dom);
     }
 
+    /**
+     * Extract envelope data from an XML document containing an <me:env> or <me:provenance> element.
+     *
+     * @param DOMDocument $dom
+     * @return mixed associative array of envelope data, or false on unrecognized input
+     *
+     * @fixme it might be easier to work with storing envelope data these in the object instead of passing arrays around
+     * @fixme may give fatal errors if some elements are missing
+     */
     public function fromDom($dom)
     {
         $env_element = $dom->getElementsByTagNameNS(MagicEnvelope::NS, 'env')->item(0);
index 963da650840ecf869fe1bc868779f3ad67d1508a..6137f7bee5a95e624bda9ed2118e93737c843dc6 100644 (file)
@@ -38,10 +38,12 @@ class Salmon
     /**
      * Sign and post the given Atom entry as a Salmon message.
      *
-     * @fixme pass through the actor for signing?
+     * Side effects: may generate a keypair on-demand for the given user,
+     * which can be very slow on some systems.
      *
      * @param string $endpoint_uri
-     * @param string $xml
+     * @param string $xml string representation of payload
+     * @param Profile $actor local user profile whose keys to sign with
      * @return boolean success
      */
     public function post($endpoint_uri, $xml, $actor)
@@ -75,6 +77,21 @@ class Salmon
         return true;
     }
 
+    /**
+     * Encode the given string as a signed MagicEnvelope XML document,
+     * using the keypair for the given local user profile.
+     *
+     * Side effects: will create and store a keypair on-demand if one
+     * hasn't already been generated for this user. This can be very slow
+     * on some systems.
+     *
+     * @param string $text XML fragment to sign, assumed to be Atom
+     * @param Profile $actor Profile of a local user to use as signer
+     * @return string XML string representation of magic envelope
+     *
+     * @throws Exception on bad profile input or key generation problems
+     * @fixme if signing fails, this seems to return the original text without warning. Is there a reason for this?
+     */
     public function createMagicEnv($text, $actor)
     {
         $magic_env = new MagicEnvelope();
@@ -101,6 +118,19 @@ class Salmon
         return $magic_env->toXML($env);
     }
 
+    /**
+     * Check if the given magic envelope is well-formed and correctly signed.
+     * Needs to have network access to fetch public keys over the web.
+     *
+     * Side effects: exceptions and caching updates may occur during network
+     * fetches.
+     *
+     * @param string $text XML fragment of magic envelope
+     * @return boolean
+     *
+     * @throws Exception on bad profile input or key generation problems
+     * @fixme could hit fatal errors or spew output on invalid XML
+     */
     public function verifyMagicEnv($text)
     {
         $magic_env = new MagicEnvelope();