- Patched from trunk support for xid.
- Two minor fixes, also from trunk.

Change-Id: I6237842e06300541dc3f583e7fef55a5e545688e
diff --git a/include/mp4v2/itmf_tags.h b/include/mp4v2/itmf_tags.h
index 9bc186c..6304219 100644
--- a/include/mp4v2/itmf_tags.h
+++ b/include/mp4v2/itmf_tags.h
@@ -56,7 +56,7 @@
 
     const char*        name;
     const char*        artist;
-    const char*        albumArtist; 
+    const char*        albumArtist;
     const char*        album;
     const char*        grouping;
     const char*        composer;
@@ -96,7 +96,7 @@
 
     const uint8_t* podcast;
     const char*    keywords;  /* TODO: Needs testing */
-    const char*    category;    
+    const char*    category;
 
     const uint8_t* hdVideo;
     const uint8_t* mediaType;
@@ -110,6 +110,7 @@
     const uint32_t* atID;
     const uint64_t* plID;
     const uint32_t* geID;
+    const char*     xid;
 } MP4Tags;
 
 /** Allocate tags convenience structure for reading and settings tags.
@@ -213,6 +214,7 @@
 MP4V2_EXPORT void MP4TagsSetATID              ( const MP4Tags*, const uint32_t* );
 MP4V2_EXPORT void MP4TagsSetPLID              ( const MP4Tags*, const uint64_t* );
 MP4V2_EXPORT void MP4TagsSetGEID              ( const MP4Tags*, const uint32_t* );
+MP4V2_EXPORT void MP4TagsSetXID               ( const MP4Tags*, const char* );
 
 /** @} ***********************************************************************/
 
diff --git a/src/atom_standard.cpp b/src/atom_standard.cpp
index 8d2e101..4b831d2 100644
--- a/src/atom_standard.cpp
+++ b/src/atom_standard.cpp
@@ -184,7 +184,8 @@
         ExpectChildAtom("catg", Optional, OnlyOne); /* Category (for podcasts?) */
         ExpectChildAtom("purl", Optional, OnlyOne); /* Podcast URL */
         ExpectChildAtom("egid", Optional, OnlyOne); /* Podcast episode global unique ID */
-        
+        ExpectChildAtom("cprt", Optional, OnlyOne); /* Copyright */
+        ExpectChildAtom("xid ", Optional, OnlyOne); /* XID */
     }  else if (ATOMID(type) == ATOMID("imif")) {
         AddVersionAndFlags();
         AddProperty(new MP4DescriptorProperty("ipmp_desc", MP4IPMPDescrTag,
diff --git a/src/cmeta.cpp b/src/cmeta.cpp
index fb47c6a..73e1573 100644
--- a/src/cmeta.cpp
+++ b/src/cmeta.cpp
@@ -1296,6 +1296,14 @@
     cpp.c_setInteger( value, cpp.geID, c.geID );
 }
 
+void
+MP4TagsSetXID( const MP4Tags* m, const char* value )
+{
+    itmf::Tags& cpp = *static_cast<itmf::Tags*>(m->__handle);
+    MP4Tags& c = *const_cast<MP4Tags*>(m);
+    cpp.c_setString( value, cpp.xid, c.xid );
+}
+
 ///////////////////////////////////////////////////////////////////////////////
 
 MP4ItmfItem*
diff --git a/src/itmf/Tags.cpp b/src/itmf/Tags.cpp
index 6982bc5..e71e88e 100644
--- a/src/itmf/Tags.cpp
+++ b/src/itmf/Tags.cpp
@@ -134,6 +134,7 @@
     fetchInteger( cim, CODE_ATID,              atID,              c.atID );
     fetchInteger( cim, CODE_PLID,              plID,              c.plID );
     fetchInteger( cim, CODE_GEID,              geID,              c.geID );
+    fetchString(  cim, CODE_XID,               xid,               c.xid );
 
     genericItemListFree( itemList ); // free
 
@@ -388,6 +389,7 @@
     storeInteger( file, CODE_ATID,              atID,              c.atID );
     storeInteger( file, CODE_PLID,              plID,              c.plID );
     storeInteger( file, CODE_GEID,              geID,              c.geID );
+    storeString(  file, CODE_XID,               xid,               c.xid );
 
     // destroy all cover-art then add each
     {
@@ -729,7 +731,7 @@
 Tags::storeTrack( MP4File& file, const MP4TagTrack& cpp, const MP4TagTrack* c )
 {
     if( c ) {
-        uint8_t buf[7];
+        uint8_t buf[8]; // iTMF spec says 7 but iTunes media is 8
         memset( buf, 0, sizeof(buf) );
 
         buf[2] = uint8_t((cpp.index & 0xff00) >> 8);
@@ -935,6 +937,7 @@
 const string Tags::CODE_ATID              = "atID";
 const string Tags::CODE_PLID              = "plID";
 const string Tags::CODE_GEID              = "geID";
+const string Tags::CODE_XID               = "xid ";
 
 ///////////////////////////////////////////////////////////////////////////////
 
diff --git a/src/itmf/Tags.h b/src/itmf/Tags.h
index 5842adf..fa604c9 100644
--- a/src/itmf/Tags.h
+++ b/src/itmf/Tags.h
@@ -85,6 +85,7 @@
     static const string CODE_ATID;
     static const string CODE_PLID;
     static const string CODE_GEID;
+    static const string CODE_XID;
 
 public:
     string      name;
@@ -142,6 +143,7 @@
     uint32_t atID;
     uint64_t plID;
     uint32_t geID;
+    string   xid;
 
 public:
     Tags();
diff --git a/util/mp4info.cpp b/util/mp4info.cpp
index f021071..947a379 100644
--- a/util/mp4info.cpp
+++ b/util/mp4info.cpp
@@ -207,6 +207,9 @@
             if ( tags->cnID ) {
                 fprintf( stdout, " cnID: %u\n", *tags->cnID );
             }
+            if ( tags->xid ) {
+                fprintf( stdout, " xid: %s\n", tags->xid );
+            }
             if ( tags->iTunesAccount ) {
                 fprintf( stdout, " iTunes Account: %s\n", tags->iTunesAccount );
             }
diff --git a/util/mp4tags.cpp b/util/mp4tags.cpp
index 04e712e..36a0843 100644
--- a/util/mp4tags.cpp
+++ b/util/mp4tags.cpp
@@ -50,12 +50,13 @@
 #define OPT_TVSHOW       'S'
 #define OPT_TRACK        't'
 #define OPT_TRACKS       'T'
+#define OPT_XID          'x'
 #define OPT_COMPOSER     'w'
 #define OPT_RELEASEDATE  'y'
 #define OPT_REMOVE       'r'
 #define OPT_ALBUM_ARTIST 'R'
 
-#define OPT_STRING  "A:a:b:c:C:d:D:e:E:g:G:H:i:I:l:L:m:M:n:N:o:P:s:S:t:T:w:y:r:R:"
+#define OPT_STRING  "A:a:b:c:C:d:D:e:E:g:G:H:i:I:l:L:m:M:n:N:o:P:s:S:t:T:x:w:y:r:R:"
 
 #define ELEMENT_OF(x,i) x[int(i)]
 
@@ -91,6 +92,7 @@
     "  -S  -show        STR  Set the TV show\n"
     "  -t, -track       NUM  Set the track number\n"
     "  -T, -tracks      NUM  Set the number of tracks\n"
+    "  -x, -xid         STR  Set the globally-unique xid (vendor:scheme:id)\n"
     "  -w, -writer      STR  Set the composer information\n"
     "  -y, -year        NUM  Set the release date\n"
     "  -R, -albumartist STR  Set the album artist\n"
@@ -129,6 +131,7 @@
         { "tempo",       prog::Option::REQUIRED_ARG, 0, OPT_TEMPO        },
         { "track",       prog::Option::REQUIRED_ARG, 0, OPT_TRACK        },
         { "tracks",      prog::Option::REQUIRED_ARG, 0, OPT_TRACKS       },
+        { "xid",         prog::Option::REQUIRED_ARG, 0, OPT_XID          },
         { "writer",      prog::Option::REQUIRED_ARG, 0, OPT_COMPOSER     },
         { "year",        prog::Option::REQUIRED_ARG, 0, OPT_RELEASEDATE  },
         { "remove",      prog::Option::REQUIRED_ARG, 0, OPT_REMOVE       },
@@ -297,6 +300,9 @@
                     case OPT_TVSHOW:
                         MP4TagsSetTVShow( mdata, NULL );
                         break;
+                    case OPT_XID:
+                        MP4TagsSetXID( mdata, NULL );
+                        break;
                     case OPT_COMPOSER:
                         MP4TagsSetComposer( mdata, NULL );
                         break;
@@ -481,6 +487,9 @@
                             fprintf( stderr, "Art file %s not found\n", tags[i] );
                         }
                     }
+                    case OPT_XID:
+                        MP4TagsSetXID( mdata, tags[i] );
+                        break;
                 }
             }
         }