1/*
2 * Copyright (C) 2014 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17/*
18 *  DESCRIPTION:
19 *      The dmtPlugin.cc file contains helper classes implementation
20 *      of plug-in API
21 */
22
23#include "jem_defs.hpp"
24#include "dmt.hpp"
25#include "dmMemory.h"
26#include "xpl_Logger.h"
27#include "dmtPlugin.hpp"
28#include "dm_tree_class.H"
29
30//////////////////////////////////////////////////////////////////
31// overlay plug-in support
32SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::OnAdd( CPCHAR path, DmtOverlayPluginData& data )
33{
34    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
35}
36
37SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::OnDelete( CPCHAR path )
38{
39    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
40}
41
42SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::Synchronize( const char* path, DMVector<DmtOverlayPluginSyncData>& data )
43{
44   return SYNCML_DM_FEATURE_NOT_SUPPORTED;
45}
46
47void DmtAPIPluginTree::Release()
48{
49    m_oAddedNodes.clear();
50}
51
52
53SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::Flush()
54{
55    m_oAddedNodes.clear();
56    return SYNCML_DM_SUCCESS;
57}
58
59SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::FindAddedNode(CPCHAR path)
60{
61    INT32 index;
62    DMString pathTmp;
63
64    for (index = 0; index < m_oAddedNodes.size(); index++)
65    {
66         m_oAddedNodes[index]->GetPath(pathTmp);
67         if ( pathTmp == path )
68             return SYNCML_DM_SUCCESS;
69    }
70
71    return SYNCML_DM_NOT_FOUND;
72
73}
74
75
76SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::FindAddedParentNode(CPCHAR path)
77{
78    SYNCML_DM_RET_STATUS_T dm_stat = SYNCML_DM_NOT_FOUND;
79
80    if ( path == NULL)
81        return dm_stat;
82
83    DMString pStr = path;
84    char * pParent = (char*)DmStrrchr(pStr,'/');
85    if ( pParent != 0 )
86    {
87        *pParent = '\0';
88        while ( pParent != NULL )
89        {
90             dm_stat = FindAddedNode(pStr);
91             if ( dm_stat == SYNCML_DM_SUCCESS )
92                return dm_stat;
93             pParent = (char*)DmStrrchr(pStr,'/');
94             if ( pParent )
95                 *pParent = '\0';
96        }
97    }
98    return dm_stat;
99
100}
101
102
103SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::SetAddedNode(PDmtNode ptrNode)
104{
105     m_oAddedNodes.push_back(ptrNode);
106     return SYNCML_DM_SUCCESS;
107}
108
109SYNCML_DM_RET_STATUS_T DmtAPIPluginTree::RemoveAddedNode(CPCHAR path)
110{
111     INT32 index;
112     INT32 size = m_oAddedNodes.size();
113     INT32 length = DmStrlen(path);
114     DMString pathTmp;
115
116     for (index = size-1; index >= 0; index--)
117     {
118          m_oAddedNodes[index]->GetPath(pathTmp);
119          if ( DmStrncmp(path,pathTmp,length) == 0 )
120               m_oAddedNodes.remove(index);
121     }
122     return SYNCML_DM_SUCCESS;
123
124}
125
126BOOLEAN DmtAPIPluginTree::SetPrincipal(CPCHAR strPrincipal)
127{
128    m_Principal.assign(strPrincipal);
129    return TRUE;
130}
131
132DmtPrincipal DmtAPIPluginTree::GetPrincipal() const
133{
134    return m_Principal;
135}
136
137// this function should be called only from the plug-in "getNode" function;
138// returns cached PDs and metaNodeID (or -1 if not set) for the current node.
139extern "C" const DmtOPINodeData* DmtGetCachedOPINodeData()
140{
141    return dmTreeObj.GetCachedOPINodeData();
142}
143
144extern "C" SYNCML_DM_RET_STATUS_T DmtSetOPINodeData( CPCHAR szURI, const DmtOverlayPluginData& oData )
145{
146    return dmTreeObj.SetOPINodeData(szURI, oData);
147}
148
149
150
151//////////////////////////////////////////////////////////////////
152//
153// DmtPluginTree
154// In this Plugin Tree, we main tain code relationship
155//
156// All path are local
157// node paths are
158//
159// ""    -- root node
160// "L1"  -- child node under root node
161// "L1/L2" -- sub children
162//
163DmtPluginTree::DmtPluginTree()
164{
165    XPL_LOG_DM_PLG_Debug(("DmtPluginTree::DmtPluginTree()"));
166}
167
168DmtPluginTree::~DmtPluginTree()
169{
170    Release();
171}
172
173
174SYNCML_DM_RET_STATUS_T DmtPluginTree::Init( CPCHAR rootNodePath )
175{
176    m_strRootPath=rootNodePath;
177    if ( rootNodePath && rootNodePath[0] )
178    {
179        if ( m_strRootPath == NULL )
180        {
181            XPL_LOG_DM_PLG_Debug(("DmtPluginTree::Init() SYNCML_DM_DEVICE_FULL\n"));
182            return SYNCML_DM_DEVICE_FULL;
183        }
184    }
185    return SYNCML_DM_SUCCESS;
186}
187
188
189SYNCML_DM_RET_STATUS_T  DmtPluginTree::GetFullPath(CPCHAR path, DMString & fullPath) const
190{
191    path = DmtGetSafeStrPtr( path );
192    fullPath = m_strRootPath;
193
194    if ( path[0] == '/' )
195        fullPath += path;
196    else
197    {
198        fullPath += "/";
199        fullPath += path;
200    }
201
202    if ( path[0] != 0 )
203        return SYNCML_DM_SUCCESS;
204
205    // remove trailing '/'
206    INT32 nLen = fullPath.length();
207
208    if ( nLen == 0 )
209    {
210        fullPath = ".";
211        return SYNCML_DM_SUCCESS;
212    }
213
214    if ( fullPath[nLen-1] == '/' )
215        fullPath.SetAt(nLen-1,0);
216
217    return SYNCML_DM_SUCCESS;
218}
219
220//
221//DmtPluginTree and DmtPluginNode all uses DmtPluginTree::GetNode
222//
223SYNCML_DM_RET_STATUS_T DmtPluginTree::GetNode(CPCHAR path,
224                                               PDmtNode& ptrNode )
225{
226    DMString strPath(path);
227
228    BOOLEAN result= FALSE;
229
230    result= m_Nodes.lookup(strPath, ptrNode);
231    XPL_LOG_DM_PLG_Debug(("GetNode lookup for %s=%d\n", path, result));
232    if (!result)
233        return SYNCML_DM_NOT_FOUND;
234
235    return SYNCML_DM_SUCCESS;
236}
237
238SYNCML_DM_RET_STATUS_T DmtPluginTree::GetChildNodeNames(
239                                               CPCHAR path,
240                                               DMStringVector &  aChildren )
241{
242    SYNCML_DM_RET_STATUS_T dm_stat;
243
244    XPL_LOG_DM_PLG_Debug(("GetChildNodeNames lookup for %s\n", path));
245    PDmtNode ptrNode;
246    DmtData oData;
247
248    dm_stat = GetNode( path, ptrNode);
249    if (dm_stat != SYNCML_DM_SUCCESS)
250    {
251        XPL_LOG_DM_PLG_Debug(("GetNode err=%d\n", dm_stat));
252        return dm_stat;
253    }
254
255    dm_stat = ptrNode->GetValue( oData );
256    if (dm_stat != SYNCML_DM_SUCCESS)
257    {
258        XPL_LOG_DM_PLG_Debug(("GetValue err=%d\n", dm_stat));
259        return dm_stat;
260    }
261
262    if (oData.GetType() != SYNCML_DM_DATAFORMAT_NODE )
263        return SYNCML_DM_FAIL;
264
265    dm_stat = oData.GetNodeValue( aChildren );
266    return dm_stat;
267}
268
269SYNCML_DM_RET_STATUS_T DmtPluginTree::DeleteNode( CPCHAR path )
270{
271    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
272}
273
274SYNCML_DM_RET_STATUS_T DmtPluginTree::RenameNode( CPCHAR path,
275                                                       CPCHAR szNewNodeName )
276{
277    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
278}
279
280SYNCML_DM_RET_STATUS_T DmtPluginTree::CreateLeafNode( CPCHAR path,
281                                                          PDmtNode& ptrCreatedNode,
282                                                          const DmtData& value )
283{
284    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
285}
286SYNCML_DM_RET_STATUS_T DmtPluginTree::CreateLeafNode(CPCHAR path,
287                              PDmtNode& ptrCreatedNode,
288                              const DmtData& value ,
289                              BOOLEAN isESN)
290{
291    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
292}
293
294SYNCML_DM_RET_STATUS_T DmtPluginTree::CreateInteriorNode( CPCHAR path,
295                                                             PDmtNode& ptrCreatedNode )
296{
297    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
298}
299
300SYNCML_DM_RET_STATUS_T DmtPluginTree::Clone(CPCHAR path,
301                                             CPCHAR szNewNodename)
302{
303    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
304}
305
306SYNCML_DM_RET_STATUS_T DmtPluginTree::GetChildValuesMap( CPCHAR path,
307                                                             DMMap<DMString, DmtData>& mapNodes )
308{
309    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
310}
311
312SYNCML_DM_RET_STATUS_T DmtPluginTree::SetChildValuesMap( CPCHAR path,
313                                                             const DMMap<DMString, DmtData>& mapNodes )
314{
315    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
316}
317
318SYNCML_DM_RET_STATUS_T DmtPluginTree::Flush()
319{
320    return DmtAPIPluginTree::Flush();
321}
322
323BOOLEAN DmtPluginTree::IsAtomic() const
324{
325    return FALSE;
326}
327
328SYNCML_DM_RET_STATUS_T DmtPluginTree::Begin()
329{
330   #ifdef DM_ATOMIC_SUPPORTED
331    return SYNCML_DM_SUCCESS;
332   #else
333    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
334   #endif
335}
336
337SYNCML_DM_RET_STATUS_T DmtPluginTree::Commit()
338{
339   #ifdef DM_ATOMIC_SUPPORTED
340    return SYNCML_DM_SUCCESS;
341   #else
342    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
343   #endif
344}
345
346SYNCML_DM_RET_STATUS_T DmtPluginTree::Rollback()
347{
348   #ifdef DM_ATOMIC_SUPPORTED
349    return SYNCML_DM_SUCCESS;
350   #else
351    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
352   #endif
353}
354
355SYNCML_DM_RET_STATUS_T DmtPluginTree::Verify()
356{
357   //For future expansion. Currently not used
358    return SYNCML_DM_SUCCESS;
359}
360
361SYNCML_DM_RET_STATUS_T DmtPluginTree::GetParameter(CPCHAR name,
362                                                    DMString & value)
363{
364    DMPluginManager & oPluginManager = dmTreeObj.GetPluginManager();
365
366    PDMPlugin pPlugin = oPluginManager.FindPlugin(SYNCML_DM_DATA_PLUGIN, m_strRootPath.c_str());
367    XPL_LOG_DM_PLG_Debug(("GetParameter name=%s\n", name));
368
369    DMStringMap maps=pPlugin->GetParameters();
370    DMString strName=name;
371
372    return maps.lookup(strName, value) ? SYNCML_DM_SUCCESS : SYNCML_DM_NOT_FOUND;
373}
374
375//
376// Helper set Functions for shared library developer to use
377//
378SYNCML_DM_RET_STATUS_T DmtPluginTree::SetNode(CPCHAR path,
379                                              PDmtNode node)
380{
381    m_Nodes.put(path, node);
382    XPL_LOG_DM_PLG_Debug(("Set Node for %s\n", path));
383    return SYNCML_DM_SUCCESS;
384}
385
386SYNCML_DM_RET_STATUS_T DmtPluginTree::RemoveNode(CPCHAR path)
387{
388    m_Nodes.remove(path);
389    XPL_LOG_DM_PLG_Debug(("Remove Node  %s\n", path));
390    return SYNCML_DM_SUCCESS;
391}
392
393SYNCML_DM_RET_STATUS_T DmtPluginTree::ClearNodes()
394{
395    m_Nodes.clear();
396    return SYNCML_DM_SUCCESS;
397}
398
399void DmtPluginTree::Release()
400{
401    DmtAPIPluginTree::Release();
402    m_Nodes.clear();
403}
404
405//
406// DmtPluginNode
407//
408
409DmtPluginNode::DmtPluginNode()
410{
411    m_bLeaf = FALSE;
412}
413
414
415SYNCML_DM_RET_STATUS_T DmtPluginNode::InitAttributes(SYNCML_DM_DATAFORMAT_T type)
416{
417
418    if (type == SYNCML_DM_DATAFORMAT_NODE)
419        m_bLeaf = FALSE;
420    else
421        m_bLeaf = TRUE;
422
423    DMString strFormat;
424   if (type<0 ||DMTree::ConvertFormat(type, strFormat) != SYNCML_DM_SUCCESS)
425    {
426       strFormat = "node";
427    }
428
429    return m_oAttr.Set(m_strName,strFormat.c_str(),"","text/plain",0,0,JemDate(),DmtAcl());
430}
431
432
433
434SYNCML_DM_RET_STATUS_T DmtPluginNode::Init(PDmtPluginTree ptrTree,
435                                        CPCHAR path)
436{
437    DMString fullPath; // DP: since this string is used all over the function ('name' pointer), moved declaration to the up
438
439    m_ptrTree=ptrTree;
440    m_strName = NULL;
441    m_strPath = NULL;
442    m_bESN = FALSE;
443    if ( path && path[0] )
444    {
445        m_strPath=path;
446        if ( m_strPath == NULL )
447            return SYNCML_DM_DEVICE_FULL;
448    }
449    m_bLeaf=FALSE;
450
451   //Name starts with relative PATH ONLY ?
452   if ( path )
453   {
454        SYNCML_DM_RET_STATUS_T dm_stat;
455        CPCHAR name = DmStrrchr(m_strPath.c_str(), '/');
456
457        if (name != NULL)
458            name++;
459        else
460        {
461            if (path[0] != 0)
462                name=m_strPath.c_str();
463            else // relative path is NULL, use last part of root node name
464            {
465                dm_stat = ptrTree->GetFullPath(path,fullPath);
466                if ( dm_stat == SYNCML_DM_SUCCESS )
467                {
468                    name=DmStrrchr(fullPath.c_str(), '/');
469                    if (name != NULL)
470                        name++;
471                }
472            }
473        }
474        if ( name )
475        {
476            m_strName = name;
477            if ( m_strName == NULL )
478                return SYNCML_DM_DEVICE_FULL;
479        }
480   }
481
482   return SYNCML_DM_SUCCESS;
483}
484
485
486SYNCML_DM_RET_STATUS_T DmtPluginNode::Init(PDmtPluginTree ptrTree,
487                                           CPCHAR path,
488                                           BOOLEAN isleaf)
489{
490    SYNCML_DM_RET_STATUS_T dm_stat;
491
492    dm_stat = Init(ptrTree,path);
493    if ( dm_stat != SYNCML_DM_SUCCESS )
494        return dm_stat;
495
496    XPL_LOG_DM_PLG_Debug(("DmtPluginNode::Init, %s, type=%d\n", m_strPath.c_str(), m_oData.GetType()));
497
498    if (isleaf)  // derived class needs to override this for special formats (INT, BINARY, etc)
499        return InitAttributes(SYNCML_DM_DATAFORMAT_STRING);
500    else
501        return InitAttributes(SYNCML_DM_DATAFORMAT_NODE);
502
503}
504
505SYNCML_DM_RET_STATUS_T DmtPluginNode::Init(PDmtPluginTree ptrTree,
506                                      CPCHAR path,
507                                      const DmtData & oData,
508                                      BOOLEAN isESN)
509{
510    SYNCML_DM_RET_STATUS_T dm_stat;
511    INT32 dataSize = 0;
512    SYNCML_DM_DATAFORMAT_T type = oData.GetType();
513
514    dm_stat = Init(ptrTree,path);
515    if ( dm_stat != SYNCML_DM_SUCCESS )
516        return dm_stat;
517
518    m_bESN = isESN;
519
520    if(m_bESN)
521    {
522        if (type == SYNCML_DM_DATAFORMAT_NULL ||
523            type == SYNCML_DM_DATAFORMAT_INT ||
524            type == SYNCML_DM_DATAFORMAT_UNDEFINED)
525        type = SYNCML_DM_DATAFORMAT_STRING;
526    }
527
528    dm_stat = m_oData.Set(oData);
529
530    if ( dm_stat != SYNCML_DM_SUCCESS )
531        return dm_stat;
532    XPL_LOG_DM_PLG_Debug(("DmtPluginNode::Init, %s, type=%d\n", m_strPath.c_str(), m_oData.GetType()));
533    dm_stat = InitAttributes(type);
534    if ( dm_stat != SYNCML_DM_SUCCESS )
535        return dm_stat;
536
537    // Get data size
538   if(!m_bESN)
539   {
540    dm_stat = m_oData.GetSize(dataSize);
541    if ( dm_stat != SYNCML_DM_SUCCESS )
542        return dm_stat;
543   }
544   m_oAttr.SetSize(dataSize);
545  return dm_stat;
546}
547
548SYNCML_DM_RET_STATUS_T DmtPluginNode::Init(PDmtPluginTree ptrTree,
549                                        CPCHAR path,
550                                        const DMStringVector & childNodeNames)
551{
552
553    SYNCML_DM_RET_STATUS_T dm_stat;
554
555    dm_stat = Init(ptrTree,path);
556    if ( dm_stat != SYNCML_DM_SUCCESS )
557        return dm_stat;
558
559
560    dm_stat = m_oData.SetNodeValue(childNodeNames);
561    if ( dm_stat != SYNCML_DM_SUCCESS )
562        return dm_stat;
563
564    XPL_LOG_DM_PLG_Debug(("DmtPluginNode::Init, %s, type=%d\n", m_strPath.c_str(), m_oData.GetType()));
565
566    return InitAttributes(m_oData.GetType());
567
568}
569
570
571DmtPluginNode::~DmtPluginNode()
572{
573//    XPL_LOG_DM_PLG_Debug(("DmtPluginNode::~DmtPluginNode, %s, type=%d\n", m_strPath.c_str(), m_oData.GetType()));
574    m_ptrTree =NULL;
575}
576
577SYNCML_DM_RET_STATUS_T DmtPluginNode::GetTree( PDmtTree& ptrTree ) const
578{
579    ptrTree = PDmtTree(m_ptrTree.GetPtr());
580    return SYNCML_DM_SUCCESS;
581}
582
583SYNCML_DM_RET_STATUS_T DmtPluginNode::GetPath(DMString & path) const
584{
585    path = m_strPath;
586    if ( m_strPath != NULL && path == NULL )
587        return SYNCML_DM_DEVICE_FULL;
588    return SYNCML_DM_SUCCESS;
589}
590
591SYNCML_DM_RET_STATUS_T DmtPluginNode::GetAttributes( DmtAttributes& oAttr ) const
592{
593    return oAttr.Set(m_oAttr);
594}
595
596SYNCML_DM_RET_STATUS_T DmtPluginNode::SetTitle( CPCHAR szTitle )
597{
598    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
599}
600
601SYNCML_DM_RET_STATUS_T DmtPluginNode::SetAcl( const DmtAcl& oAcl )
602{
603    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
604}
605
606SYNCML_DM_RET_STATUS_T DmtPluginNode::GetValue( DmtData& oData ) const
607{
608    XPL_LOG_DM_PLG_Debug(("DmtPluginNode::GetValue, this=0x%x %s, type=%d\n", this, m_strPath.c_str(), m_oData.GetType()));
609    return oData.Set(m_oData);
610}
611
612SYNCML_DM_RET_STATUS_T DmtPluginNode::SetValue( const DmtData& value )
613{
614    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
615}
616
617BOOLEAN DmtPluginNode::IsLeaf() const
618{
619    return m_bLeaf;
620}
621
622SYNCML_DM_RET_STATUS_T DmtPluginNode::GetChildNode( CPCHAR szPath, PDmtNode& ptrNode )
623{
624    if ( m_bLeaf )
625        return SYNCML_DM_FEATURE_NOT_SUPPORTED;
626
627    DMString oChildPath(m_strPath);
628    oChildPath +="/";
629    oChildPath += DmtGetSafeStrPtr( szPath );
630    return m_ptrTree->GetNode(oChildPath.c_str(), ptrNode);
631}
632
633SYNCML_DM_RET_STATUS_T DmtPluginNode::Execute( CPCHAR strData, DMString& result )
634{
635    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
636}
637
638SYNCML_DM_RET_STATUS_T DmtPluginNode::GetNodeName(DMString & name) const
639{
640    name = m_strName;
641    if ( m_strName != NULL && name == NULL )
642        return SYNCML_DM_DEVICE_FULL;
643    return SYNCML_DM_SUCCESS;
644}
645
646SYNCML_DM_RET_STATUS_T DmtPluginNode::Rename( CPCHAR szNewName )
647{
648    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
649}
650
651SYNCML_DM_RET_STATUS_T DmtPluginNode::GetChildNodes( DMVector<PDmtNode>& oChildren ) const
652{
653    XPL_LOG_DM_PLG_Debug(("GetChildNodes for %s\n", m_strPath.c_str()));
654
655    oChildren.clear(); // remove all previous items from array
656
657    if ( m_bLeaf )
658        return SYNCML_DM_FAIL;
659
660    DmtData oData;
661
662    SYNCML_DM_RET_STATUS_T dm_stat = GetValue( oData );
663
664    if ( dm_stat != SYNCML_DM_SUCCESS )
665        return dm_stat;
666
667    const DMStringVector & aChildren = oData.GetNodeValue();
668
669    XPL_LOG_DM_PLG_Debug(("aChildren.size()=%d\n", aChildren.size()));
670
671    for ( INT32 i = 0; i < aChildren.size(); i++ )
672    {
673        DMString strChildPath = m_strPath;
674
675        if (strChildPath.length() != 0)
676            strChildPath += "/";
677        strChildPath += aChildren[i];
678
679        PDmtNode ptrNode;
680
681        XPL_LOG_DM_PLG_Debug(("Get child[%d], path=%s\n", i, strChildPath.c_str()));
682        dm_stat = m_ptrTree->GetNode( strChildPath.c_str(), ptrNode );
683        if ( dm_stat != SYNCML_DM_SUCCESS )
684            return dm_stat;
685
686        oChildren.push_back( ptrNode );
687    }
688
689    return dm_stat;
690}
691
692SYNCML_DM_RET_STATUS_T DmtPluginNode::GetFirstChunk(DmtDataChunk&  dmtChunkData)
693{
694    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
695}
696
697SYNCML_DM_RET_STATUS_T DmtPluginNode::GetNextChunk(DmtDataChunk& dmtChunkData)
698{
699    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
700}
701
702SYNCML_DM_RET_STATUS_T DmtPluginNode::SetFirstChunk(DmtDataChunk& dmtChunkData)
703{
704    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
705}
706
707SYNCML_DM_RET_STATUS_T DmtPluginNode::SetNextChunk(DmtDataChunk& dmtChunkData)
708{
709    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
710}
711
712SYNCML_DM_RET_STATUS_T DmtPluginNode::SetLastChunk(DmtDataChunk& dmtChunkData)
713{
714    return SYNCML_DM_FEATURE_NOT_SUPPORTED;
715}
716