Index: branches/SHM-4.1-dev/source/App/TAppEncoder/TAppEncTop.cpp
===================================================================
--- branches/SHM-4.1-dev/source/App/TAppEncoder/TAppEncTop.cpp	(revision 515)
+++ branches/SHM-4.1-dev/source/App/TAppEncoder/TAppEncTop.cpp	(revision 516)
@@ -90,4 +90,5 @@
     vps->setMaxDecPicBuffering             ( m_maxDecPicBuffering[i], i );
   }
+
 #if REPN_FORMAT_IN_VPS
   vps->setRepFormatIdxPresentFlag( true );   // Could be disabled to optimize in some cases.
@@ -1191,4 +1192,59 @@
   }
 #endif
+ #if VPS_DPB_SIZE_TABLE
+  // The Layer ID List variables can be derived here.  
+#if DERIVE_LAYER_ID_LIST_VARIABLES
+  vps->deriveLayerIdListVariables();
+#endif
+  vps->deriveNumberOfSubDpbs();
+  // Initialize dpb_size_table() for all ouput layer sets in the VPS extension
+  for(i = 1; i < vps->getNumOutputLayerSets(); i++)
+  {
+    Int layerSetId = vps->getOutputLayerSetIdx(i);
+
+    // For each output layer set, set the DPB size for each layer and the reorder/latency value the maximum for all layers
+    Bool checkFlagOuter = false;      // Used to calculate sub_layer_flag_info_present_flag
+    Bool checkFlagInner[MAX_TLAYER];  // Used to calculate sub_layer_dpb_info_present_flag
+
+    for(Int j = 0; j < vps->getMaxTLayers(); j++)
+    {
+
+      Int maxNumReorderPics = -1;
+      for(Int k = 0; k < vps->getNumSubDpbs(i); k++)
+      {
+        Int layerId = vps->getLayerSetLayerIdList(layerSetId, k); // k-th layer in the output layer set
+        vps->setMaxVpsDecPicBufferingMinus1( i, k, j,  m_acTEncTop[layerId].getMaxDecPicBuffering(j) );
+        maxNumReorderPics       = std::max( maxNumReorderPics, m_acTEncTop[layerId].getNumReorderPics(j));
+      }
+      vps->setMaxVpsNumReorderPics(i, j, maxNumReorderPics);
+      
+      if( j == 0 )  // checkFlagInner[0] is always 1
+      {
+        checkFlagInner[j] = true;     // Always signal sub-layer DPB information for the first sub-layer
+      }
+      else
+      {
+        checkFlagInner[j] = false;    // Initialize to be false. If the values of the current sub-layers matches with the earlier sub-layer, 
+                                      // then will be continue to be false - i.e. the j-th sub-layer DPB info is not signaled
+        checkFlagInner[j] |= ( maxNumReorderPics != vps->getMaxVpsNumReorderPics(i, j - 1) );
+        for(Int k = 0; k < vps->getNumSubDpbs(i) && !checkFlagInner[j]; k++)  // If checkFlagInner[j] is true, break and signal the values
+        {
+          checkFlagInner[j] |= ( vps->getMaxVpsDecPicBufferingMinus1(i, k, j - 1) != vps->getMaxVpsDecPicBufferingMinus1(i, k, j) );
+        }
+      }
+      // If checkFlagInner[j] = true, then some value needs to be signalled for the j-th sub-layer
+      vps->setSubLayerDpbInfoPresentFlag( i, j, checkFlagInner[j] );
+    }
+    for(Int j = 1; j < vps->getMaxTLayers(); j++) // Check if DPB info of any of non-zero sub-layers is signaled. If so set flag to one
+    {
+      if( vps->getSubLayerDpbInfoPresentFlag(i, j) )
+      {
+        checkFlagOuter = true;
+        break;
+      }
+    }
+    vps->setSubLayerFlagInfoPresentFlag( i, checkFlagOuter );
+  }
+#endif
 #if VPS_EXTN_DIRECT_REF_LAYERS
   // Direct reference layers
Index: branches/SHM-4.1-dev/source/Lib/TLibCommon/TComSlice.cpp
===================================================================
--- branches/SHM-4.1-dev/source/Lib/TLibCommon/TComSlice.cpp	(revision 515)
+++ branches/SHM-4.1-dev/source/Lib/TLibCommon/TComSlice.cpp	(revision 516)
@@ -946,5 +946,5 @@
     numRpsCurrTempList += getNumILRRefIdx();
 #endif
-  }
+}
 #endif
 
@@ -2144,4 +2144,12 @@
   }
 #endif
+#if VPS_DPB_SIZE_TABLE
+  ::memset( m_subLayerFlagInfoPresentFlag,  0, sizeof(m_subLayerFlagInfoPresentFlag ) );
+  ::memset( m_subLayerDpbInfoPresentFlag,   0, sizeof(m_subLayerDpbInfoPresentFlag )  );
+  ::memset( m_maxVpsDecPicBufferingMinus1,  0, sizeof(m_maxVpsDecPicBufferingMinus1 ) );
+  ::memset( m_maxVpsNumReorderPics,         0, sizeof(m_maxVpsNumReorderPics )        );
+  ::memset( m_maxVpsLatencyIncreasePlus1,   0, sizeof(m_maxVpsLatencyIncreasePlus1 )  );
+  ::memset( m_numSubDpbs                ,   0, sizeof(m_numSubDpbs)                   );
+#endif
 }
 #else
@@ -2193,4 +2201,17 @@
     }
     setNumLayersInIdList(i, n);
+  }
+}
+#endif
+#if VPS_DPB_SIZE_TABLE
+Void TComVPS::deriveNumberOfSubDpbs()
+{
+  // Derive number of sub-DPBs
+  // For output layer set 0
+  setNumSubDpbs(0, 1);
+  // For other output layer sets
+  for( Int i = 1; i < getNumOutputLayerSets(); i++)
+  {
+    setNumSubDpbs( i, getNumLayersInIdList( getOutputLayerSetIdx(i)) );
   }
 }
Index: branches/SHM-4.1-dev/source/Lib/TLibCommon/TComSlice.h
===================================================================
--- branches/SHM-4.1-dev/source/Lib/TLibCommon/TComSlice.h	(revision 515)
+++ branches/SHM-4.1-dev/source/Lib/TLibCommon/TComSlice.h	(revision 516)
@@ -642,4 +642,12 @@
   Bool       m_recursiveRefLayerFlag[MAX_NUM_LAYER_IDS][MAX_NUM_LAYER_IDS];  // flag to indicate if j-th layer is a direct or indirect reference layer of i-th layer
 #endif
+#if VPS_DPB_SIZE_TABLE
+  Bool    m_subLayerFlagInfoPresentFlag [MAX_VPS_OP_LAYER_SETS_PLUS1];
+  Bool    m_subLayerDpbInfoPresentFlag  [MAX_VPS_OP_LAYER_SETS_PLUS1][MAX_LAYERS];
+  Int     m_maxVpsDecPicBufferingMinus1 [MAX_VPS_OP_LAYER_SETS_PLUS1][MAX_LAYERS][MAX_TLAYER];
+  Int     m_maxVpsNumReorderPics        [MAX_VPS_OP_LAYER_SETS_PLUS1][MAX_LAYERS];
+  Int     m_maxVpsLatencyIncreasePlus1  [MAX_VPS_OP_LAYER_SETS_PLUS1][MAX_LAYERS];
+  Int     m_numSubDpbs                  [MAX_VPS_OP_LAYER_SETS_PLUS1];
+#endif
 #endif //SVC_EXTENSION
 public:
@@ -707,5 +715,7 @@
   Void    deriveLayerIdListVariables();
 #endif
-
+#if VPS_DPB_SIZE_TABLE
+Void      deriveNumberOfSubDpbs();
+#endif
 #if IL_SL_SIGNALLING_N0371
   Bool    checkLayerDependency(UInt i, UInt j);
@@ -928,4 +938,23 @@
   Bool   getPhaseAlignFlag()                             { return m_phaseAlignFlag; }
   Void   setPhaseAlignFlag(Bool x)                       { m_phaseAlignFlag = x;    }
+#endif
+#if VPS_DPB_SIZE_TABLE
+  Bool    getSubLayerFlagInfoPresentFlag(Int i)         {return m_subLayerFlagInfoPresentFlag[i]; }
+  Void    setSubLayerFlagInfoPresentFlag(Int i, Bool x) {m_subLayerFlagInfoPresentFlag[i] = x;    }
+
+  Bool    getSubLayerDpbInfoPresentFlag(Int i, Int j)         {return m_subLayerDpbInfoPresentFlag[i][j]; }
+  Void    setSubLayerDpbInfoPresentFlag(Int i, Int j, Bool x) {m_subLayerDpbInfoPresentFlag[i][j] = x;    }
+
+  Int     getMaxVpsDecPicBufferingMinus1(Int i, Int k, Int j)         { return m_maxVpsDecPicBufferingMinus1[i][k][j]; }
+  Void    setMaxVpsDecPicBufferingMinus1(Int i, Int k, Int j, Int x) { m_maxVpsDecPicBufferingMinus1[i][k][j] = x;    }
+
+  Int     getMaxVpsNumReorderPics(Int i, Int j)         { return m_maxVpsNumReorderPics[i][j]; }
+  Void    setMaxVpsNumReorderPics(Int i, Int j, Int x) { m_maxVpsNumReorderPics[i][j] = x;    }
+
+  Int     getMaxVpsLatencyIncreasePlus1(Int i, Int j)         { return m_maxVpsLatencyIncreasePlus1[i][j]; }
+  Void    setMaxVpsLatencyIncreasePlus1(Int i, Int j, Int x) { m_maxVpsLatencyIncreasePlus1[i][j] = x;    }
+
+  Int     getNumSubDpbs(Int i)                          { return m_numSubDpbs[i]; }
+  Void    setNumSubDpbs(Int i, Int x)                   { m_numSubDpbs[i] = x;    }
 #endif
 #endif //SVC_EXTENSION
Index: branches/SHM-4.1-dev/source/Lib/TLibCommon/TypeDef.h
===================================================================
--- branches/SHM-4.1-dev/source/Lib/TLibCommon/TypeDef.h	(revision 515)
+++ branches/SHM-4.1-dev/source/Lib/TLibCommon/TypeDef.h	(revision 516)
@@ -188,4 +188,5 @@
 #define O0153_ALT_OUTPUT_LAYER_FLAG      1      ///< JCTVC-O0153: alt output layer flag
 
+#define VPS_DPB_SIZE_TABLE               1      ///< JCTVC-O0217: DPB operations: signaling DPB-related parameters
 #else
 #define SYNTAX_OUTPUT                    0
@@ -206,4 +207,5 @@
 #define MAX_VPS_NUM_SCALABILITY_TYPES             16
 #endif
+#define MAX_VPS_OP_LAYER_SETS_PLUS1               3
 #if VPS_RENAME
 #define MAX_VPS_LAYER_SETS_PLUS1                  1024
Index: branches/SHM-4.1-dev/source/Lib/TLibDecoder/TDecCAVLC.cpp
===================================================================
--- branches/SHM-4.1-dev/source/Lib/TLibDecoder/TDecCAVLC.cpp	(revision 515)
+++ branches/SHM-4.1-dev/source/Lib/TLibDecoder/TDecCAVLC.cpp	(revision 516)
@@ -1259,4 +1259,7 @@
     else
     {
+#if VPS_DPB_SIZE_TABLE 
+      vps->setOutputLayerSetIdx( i, i );
+#endif
       // i <= (vps->getNumLayerSets() - 1)
       // Assign OutputLayerFlag depending on default_one_target_output_layer_flag
@@ -1372,4 +1375,38 @@
 #endif
 
+#if VPS_DPB_SIZE_TABLE
+  vps->deriveNumberOfSubDpbs();
+  for(i = 1; i < vps->getNumOutputLayerSets(); i++)
+  {
+    READ_FLAG( uiCode, "sub_layer_flag_info_present_flag[i]");  vps->setSubLayerFlagInfoPresentFlag( i, uiCode ? true : false );
+    for(j = 0; j < vps->getMaxTLayers(); j++)
+    {
+      if( j > 0 && vps->getSubLayerFlagInfoPresentFlag(i) )
+      {
+        READ_FLAG( uiCode, "sub_layer_dpb_info_present_flag[i]");  vps->setSubLayerDpbInfoPresentFlag( i, j, uiCode ? true : false);
+      }
+      else
+      {
+        if( j == 0 )  // Always signal for the first sub-layer
+        {
+          vps->setSubLayerDpbInfoPresentFlag( i, j, true );
+        }
+        else // if (j != 0) && !vps->getSubLayerFlagInfoPresentFlag(i)
+        {
+          vps->setSubLayerDpbInfoPresentFlag( i, j, false );
+        }
+      }
+      if( vps->getSubLayerDpbInfoPresentFlag(i, j) )  // If sub-layer DPB information is present
+      {
+        for(Int k = 0; k < vps->getNumSubDpbs(i); k++)
+        {
+          READ_UVLC( uiCode, "max_vps_dec_pic_buffering_minus1[i][k][j]" ); vps->setMaxVpsDecPicBufferingMinus1( i, k, j, uiCode );
+        }
+        READ_UVLC( uiCode, "max_vps_num_reorder_pics[i][j]" );              vps->setMaxVpsNumReorderPics( i, j, uiCode);
+        READ_UVLC( uiCode, "max_vps_latency_increase_plus1[i][j]" );        vps->setMaxVpsLatencyIncreasePlus1( i, j, uiCode);
+      }
+    }
+  }
+#endif
 #if VPS_EXTN_DIRECT_REF_LAYERS && M0457_PREDICTION_INDICATIONS
   READ_UVLC( uiCode,           "direct_dep_type_len_minus2"); vps->setDirectDepTypeLen(uiCode+2);
Index: branches/SHM-4.1-dev/source/Lib/TLibEncoder/TEncCavlc.cpp
===================================================================
--- branches/SHM-4.1-dev/source/Lib/TLibEncoder/TEncCavlc.cpp	(revision 515)
+++ branches/SHM-4.1-dev/source/Lib/TLibEncoder/TEncCavlc.cpp	(revision 516)
@@ -1079,4 +1079,26 @@
   WRITE_FLAG(vps->getCrossLayerIrapAlignFlag(), "cross_layer_irap_aligned_flag");
 #endif 
+#if VPS_DPB_SIZE_TABLE
+  for(i = 1; i < vps->getNumOutputLayerSets(); i++)
+  {
+    WRITE_FLAG( vps->getSubLayerFlagInfoPresentFlag( i ), "sub_layer_flag_info_present_flag[i]");  
+    for(j = 0; j < vps->getMaxTLayers(); j++)
+    {
+      if( j > 0 && vps->getSubLayerFlagInfoPresentFlag(i) )
+      {
+        WRITE_FLAG( vps->getSubLayerDpbInfoPresentFlag( i, j), "sub_layer_dpb_info_present_flag[i]");  
+      }
+      if( vps->getSubLayerDpbInfoPresentFlag(i, j) )
+      {
+        for(Int k = 0; k < vps->getNumSubDpbs(i); k++)
+        {
+          WRITE_UVLC( vps->getMaxVpsDecPicBufferingMinus1( i, k, j), "max_vps_dec_pic_buffering_minus1[i][k][j]" ); 
+        }
+        WRITE_UVLC( vps->getMaxVpsNumReorderPics( i, j), "max_vps_num_reorder_pics[i][j]" );              
+        WRITE_UVLC( vps->getMaxVpsLatencyIncreasePlus1( i, j), "max_vps_latency_increase_plus1[i][j]" );        
+      }
+    }
+  }
+#endif
 #if VPS_EXTN_DIRECT_REF_LAYERS && M0457_PREDICTION_INDICATIONS
   WRITE_UVLC( vps->getDirectDepTypeLen()-2,                           "direct_dep_type_len_minus2");
