(file) Return to CIMRepository.cpp CVS log (file) (dir) Up to [Pegasus] / pegasus / src / Pegasus / Repository

   1 mike  1.48 //%/////////////////////////////////////////////////////////////////////////////
   2            //
   3            // Copyright (c) 2000, 2001 The Open group, BMC Software, Tivoli Systems, IBM
   4            //
   5            // Permission is hereby granted, free of charge, to any person obtaining a copy
   6            // of this software and associated documentation files (the "Software"), to
   7            // deal in the Software without restriction, including without limitation the
   8            // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
   9            // sell copies of the Software, and to permit persons to whom the Software is
  10            // furnished to do so, subject to the following conditions:
  11            //
  12            // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
  13            // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
  14            // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
  15            // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
  16            // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  17            // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
  18            // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
  19            // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  20            //
  21            //==============================================================================
  22 mike  1.48 //
  23            // Author: Mike Brasher (mbrasher@bmc.com)
  24            //
  25            // Modified By:
  26            //
  27            //%/////////////////////////////////////////////////////////////////////////////
  28            
  29            #include <cctype>
  30            #include <cstdio>
  31            #include <fstream>
  32            #include <Pegasus/Common/Pair.h>
  33            #include <Pegasus/Common/Destroyer.h>
  34            #include <Pegasus/Common/FileSystem.h>
  35            #include <Pegasus/Common/Exception.h>
  36            #include <Pegasus/Common/XmlReader.h>
  37            #include <Pegasus/Common/XmlWriter.h>
  38            #include <Pegasus/Common/DeclContext.h>
  39            #include <Pegasus/Common/DeclContext.h>
  40            #include <Pegasus/Common/System.h>
  41            #include "CIMRepository.h"
  42            #include "RepositoryDeclContext.h"
  43 mike  1.48 #include "InstanceIndexFile.h"
  44            #include "AssocInstTable.h"
  45            #include "AssocClassTable.h"
  46            
  47            #define INDENT_XML_FILES
  48            
  49            PEGASUS_USING_STD;
  50            
  51            PEGASUS_NAMESPACE_BEGIN
  52            
  53            ////////////////////////////////////////////////////////////////////////////////
  54            //
  55            // _LoadObject()
  56            //
  57            //	Loads objects (classes, instances, and qualifiers) from disk to
  58            //	memory objects.
  59            //
  60            ////////////////////////////////////////////////////////////////////////////////
  61            
  62            template<class Object>
  63            void _LoadObject(
  64 mike  1.48     const String& path,
  65                Object& object)
  66            {
  67                // Get the real path of the file:
  68            
  69                String realPath;
  70            
  71                if (!FileSystem::existsNoCase(path, realPath))
  72            	throw CannotOpenFile(path);
  73            
  74                // Load file into memory:
  75            
  76                Array<Sint8> data;
  77                FileSystem::loadFileToMemory(data, realPath);
  78                data.append('\0');
  79            
  80                XmlParser parser((char*)data.getData());
  81            
  82                XmlReader::getObject(parser, object);
  83            }
  84            
  85 mike  1.48 ////////////////////////////////////////////////////////////////////////////////
  86            //
  87            // _SaveObject()
  88            //
  89            //	Saves objects (classes, instances, and qualifiers) from memory to
  90            //	disk files.
  91            //
  92            ////////////////////////////////////////////////////////////////////////////////
  93            
  94            template<class Object>
  95            void _SaveObject(const String& path, const Object& object)
  96            {
  97                Array<Sint8> out;
  98                object.toXml(out);
  99            
 100                ArrayDestroyer<char> destroyer(path.allocateCString());
 101                PEGASUS_STD(ofstream) os(destroyer.getPointer() PEGASUS_IOS_BINARY);
 102            
 103                if (!os)
 104            	throw CannotOpenFile(path);
 105            
 106 mike  1.48 #ifdef INDENT_XML_FILES
 107                out.append('\0');
 108                XmlWriter::indentedPrint(os, out.getData(), 2);
 109            #else
 110                os.write((char*)out.getData(), out.size());
 111            #endif
 112            }
 113            
 114            static String _MakeAssocInstPath(
 115                const String& nameSpace,
 116                const String& repositoryRoot)
 117            {
 118                String tmp = nameSpace;
 119                tmp.translate('/', '#');
 120                return String(Cat(repositoryRoot, "/", tmp, "/instances/associations"));
 121            }
 122            
 123            static String _MakeAssocClassPath(
 124                const String& nameSpace,
 125                const String& repositoryRoot)
 126            {
 127 mike  1.48     String tmp = nameSpace;
 128                tmp.translate('/', '#');
 129                return String(Cat(repositoryRoot, "/", tmp, "/classes/associations"));
 130            }
 131            
 132            ////////////////////////////////////////////////////////////////////////////////
 133            //
 134            // CIMRepository
 135            //
 136            //     The following are not implemented:
 137            //
 138            //         CIMRepository::setProperty()
 139            //         CIMRepository::getProperty()
 140            //         CIMRepository::modifyInstance()
 141            //         CIMRepository::execQuery()
 142            //         CIMRepository::execQuery()
 143            //         CIMRepository::associators()
 144            //         CIMRepository::associatorNames()
 145            //         CIMRepository::referencess()
 146            //         CIMRepository::referencesNames()
 147            //         CIMRepository::invokeMethod()
 148 mike  1.48 //
 149            //     Note that invokeMethod() will not never implemented since it is not
 150            //     meaningful for a repository.
 151            //
 152            //     ATTN: need to combine instances of each class into a common file to
 153            //     improve disk utilization (too many i-nodes in Unix).
 154            //
 155            //     ATTN: make operations on files non-case-sensitive.
 156            //
 157            ////////////////////////////////////////////////////////////////////////////////
 158            
 159            CIMRepository::CIMRepository(const String& repositoryRoot)
 160                : _repositoryRoot(repositoryRoot), _nameSpaceManager(repositoryRoot)
 161            {
 162                _context = new RepositoryDeclContext(this);
 163            }
 164            
 165            CIMRepository::~CIMRepository()
 166            {
 167                delete _context;
 168            }
 169 mike  1.48 
 170            CIMClass CIMRepository::getClass(
 171                const String& nameSpace,
 172                const String& className,
 173                Boolean localOnly,
 174                Boolean includeQualifiers,
 175                Boolean includeClassOrigin,
 176                const Array<String>& propertyList)
 177            {
 178                // ATTN: localOnly, includeQualifiers, and includeClassOrigin are ignored
 179                // for now.
 180            
 181                String classFilePath;
 182                classFilePath = _nameSpaceManager.getClassFilePath(nameSpace, className);
 183            
 184                CIMClass cimClass;
 185                _LoadObject(classFilePath, cimClass);
 186            
 187                return cimClass;
 188            }
 189            
 190 mike  1.48 Boolean CIMRepository::_getInstanceIndex(
 191                const String& nameSpace,
 192                const CIMReference& instanceName,
 193                String& className,
 194                Uint32& index,
 195                Boolean searchSuperClasses) const
 196            {
 197                // -- Get all descendent classes of this class:
 198            
 199                className = instanceName.getClassName();
 200            
 201                Array<String> classNames;
 202                _nameSpaceManager.getSubClassNames(nameSpace, className, true, classNames);
 203                classNames.prepend(className);
 204            
 205                // -- Get all superclasses of this one:
 206            
 207                if (searchSuperClasses)
 208            	_nameSpaceManager.getSuperClassNames(nameSpace, className, classNames);
 209            
 210                // -- Search each qualifying instance file for the instance:
 211 mike  1.48 
 212                for (Uint32 i = 0; i < classNames.size(); i++)
 213                {
 214            	CIMReference tmpInstanceName = instanceName;
 215            	tmpInstanceName.setClassName(classNames[i]);
 216            
 217            	// -- Lookup index of instance:
 218            
 219            	String path = _getIndexFilePath(nameSpace, classNames[i]);
 220            
 221            	if (InstanceIndexFile::lookup(path, tmpInstanceName, index))
 222            	{
 223            	    className = classNames[i];
 224            	    return true;
 225            	}
 226                }
 227            
 228                return false;
 229            }
 230            
 231            CIMInstance CIMRepository::getInstance(
 232 mike  1.48     const String& nameSpace,
 233                const CIMReference& instanceName,
 234                Boolean localOnly,
 235                Boolean includeQualifiers,
 236                Boolean includeClassOrigin,
 237                const Array<String>& propertyList)
 238            {
 239                // -- Get the index for this instance:
 240            
 241                String className;
 242                Uint32 index;
 243            
 244                if (!_getInstanceIndex(nameSpace, instanceName, className, index))
 245                {
 246            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_FOUND, "getInstance()");
 247                }
 248            
 249                // -- Load the instance from the file:
 250            
 251                String path = _getInstanceFilePath(nameSpace, className, index);
 252                CIMInstance cimInstance;
 253 mike  1.48     _LoadObject(path, cimInstance);
 254                return cimInstance;
 255            }
 256            
 257            void CIMRepository::deleteClass(
 258                const String& nameSpace,
 259                const String& className)
 260            {
 261                // -- Get the class and check to see if it is an association class:
 262            
 263                CIMClass cimClass = getClass(nameSpace, className, false);
 264                Boolean isAssociation = cimClass.isAssociation();
 265            
 266                // -- Disallow deletion if class has instances:
 267            
 268                String path = _getIndexFilePath(nameSpace, className);
 269                String realPath;
 270            
 271                if (FileSystem::existsNoCase(path, realPath))
 272            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_CLASS_HAS_INSTANCES, className);
 273            
 274 mike  1.48     // -- Delete the class (disallowed if there are subclasses):
 275            
 276                _nameSpaceManager.deleteClass(nameSpace, className);
 277            
 278                // -- Remove association:
 279            
 280                if (isAssociation)
 281                {
 282            	String assocFileName = _MakeAssocClassPath(nameSpace, _repositoryRoot);
 283            
 284            	if (FileSystem::exists(assocFileName))
 285            	    AssocClassTable::deleteAssociation(assocFileName, className);
 286                }
 287            }
 288            
 289            void CIMRepository::deleteInstance(
 290                const String& nameSpace,
 291                const CIMReference& instanceName)
 292            {
 293                // -- Lookup index of entry from index file:
 294            
 295 mike  1.48     String indexFilePath = _getIndexFilePath(
 296            	nameSpace, instanceName.getClassName());
 297            
 298                Uint32 index;
 299            
 300                if (!InstanceIndexFile::lookup(indexFilePath, instanceName, index))
 301            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_FOUND, instanceName.toString());
 302            
 303                // -- Attempt to remove the instance file:
 304            
 305                String instanceFilePath = _getInstanceFilePath(
 306            	nameSpace, instanceName.getClassName(), index);
 307            
 308                if (!FileSystem::removeFileNoCase(instanceFilePath))
 309                {
 310            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
 311            	    "failed to remove file in CIMRepository::deleteInstance()");
 312                }
 313            
 314                // -- Remove entry from index file:
 315            
 316 mike  1.48     InstanceIndexFile::remove(indexFilePath, instanceName);
 317            
 318                // -- Delete index file if it is now empty (zero size):
 319            
 320                Uint32 size;
 321            
 322                if (!FileSystem::getFileSizeNoCase(indexFilePath, size))
 323                {
 324            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
 325            	    "unexpected failure in CIMRepository::deleteInstance()");
 326                }
 327            
 328                if (size == 0 && !FileSystem::removeFileNoCase(indexFilePath))
 329                {
 330            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
 331            	    "unexpected failure in CIMRepository::deleteInstance()");
 332                }
 333            
 334                // -- Remove it from the association table (if it is really association).
 335                // -- We ignore the return value intentionally. If it is an association,
 336                // -- true is returned. Otherwise, true is returned.
 337 mike  1.48 
 338                String assocFileName = _MakeAssocInstPath(nameSpace, _repositoryRoot);
 339            
 340                if (FileSystem::exists(assocFileName))
 341            	AssocInstTable::deleteAssociation(assocFileName, instanceName);
 342            }
 343            
 344            void CIMRepository::_createAssocClassEntries(
 345                const String& nameSpace,
 346                const CIMConstClass& assocClass)
 347            {
 348                // Open input file:
 349            
 350                String assocFileName = _MakeAssocClassPath(nameSpace, _repositoryRoot);
 351                ofstream os;
 352            
 353                if (!OpenAppend(os, assocFileName))
 354            	throw CannotOpenFile(assocFileName);
 355            
 356                // Get the association's class name:
 357            
 358 mike  1.48     String assocClassName = assocClass.getClassName();
 359            
 360                // For each property:
 361            
 362                Uint32 n = assocClass.getPropertyCount();
 363            
 364                for (Uint32 i = 0; i < n; i++)
 365                {
 366            	CIMConstProperty fromProp = assocClass.getProperty(i);
 367            
 368            	if (fromProp.getType() == CIMType::REFERENCE)
 369            	{
 370            	    for (Uint32 j = 0; j < n; j++)
 371            	    {
 372            		CIMConstProperty toProp = assocClass.getProperty(j);
 373            
 374            		if (toProp.getType() == CIMType::REFERENCE &&
 375            		    fromProp.getName() != toProp.getName())
 376            		{
 377            		    String fromClassName = fromProp.getReferenceClassName();
 378            		    String fromPropertyName = fromProp.getName();
 379 mike  1.48 		    String toClassName = toProp.getReferenceClassName();
 380            		    String toPropertyName = toProp.getName();
 381            
 382            		    AssocClassTable::append(
 383            			os,
 384            			assocClassName,
 385            			fromClassName,
 386            			fromPropertyName,
 387            			toClassName,
 388            			toPropertyName);
 389            		}
 390            	    }
 391            	}
 392                }
 393            }
 394            
 395            void CIMRepository::createClass(
 396                const String& nameSpace,
 397                const CIMClass& newClass)
 398            {
 399                // -- Resolve the class:
 400 mike  1.48 	CIMClass cimClass(newClass);
 401            	
 402                cimClass.resolve(_context, nameSpace);
 403            
 404                // -- If an association, populate associations file:
 405            
 406                if (cimClass.isAssociation())
 407            	_createAssocClassEntries(nameSpace, cimClass);
 408            
 409                // -- Create namespace manager entry:
 410            
 411                String classFilePath;
 412            
 413                _nameSpaceManager.createClass(nameSpace, cimClass.getClassName(),
 414            	cimClass.getSuperClassName(), classFilePath);
 415            
 416                // -- Create the class file:
 417            
 418                _SaveObject(classFilePath, cimClass);
 419            }
 420            
 421 mike  1.48 /*------------------------------------------------------------------------------
 422            
 423                This routine does the following:
 424            
 425                	1.  Creates two entries in the association file for each relationship
 426            	    formed by this new assocation instance. A binary association
 427            	    (one with two references) ties two instances together. Suppose
 428            	    there are two instances: I1 and I2. Then two entries are created:
 429            
 430            		I2 -> I1
 431            		I1 -> I2
 432            
 433            	    For a ternary relationship, six entries will be created. Suppose
 434            	    there are three instances: I1, I2, and I3:
 435            
 436            		I1 -> I2
 437            		I1 -> I3
 438            		I2 -> I1
 439            		I2 -> I3
 440            		I3 -> I1
 441            		I3 -> I2
 442 mike  1.48 
 443            	    So for an N-ary relationship, there will be 2*N entries created.
 444            
 445            	2.  Verifies that the association instance refers to real objects.
 446            	    (note that an association reference may refer to either an instance
 447            	    or a class). Throws an exception if one of the references does not
 448            	    refer to a valid object.
 449            
 450            ------------------------------------------------------------------------------*/
 451            
 452            void CIMRepository::_createAssocInstEntries(
 453                const String& nameSpace,
 454                const CIMConstClass& cimClass,
 455                const CIMInstance& cimInstance,
 456                const CIMReference& instanceName)
 457            {
 458                // Open input file:
 459            
 460                String assocFileName = _MakeAssocInstPath(nameSpace, _repositoryRoot);
 461                ofstream os;
 462            
 463 mike  1.48     if (!OpenAppend(os, assocFileName))
 464            	throw CannotOpenFile(assocFileName);
 465            
 466                // Get the association's instance name and class name:
 467            
 468                String assocInstanceName = instanceName.toString();
 469                String assocClassName = instanceName.getClassName();
 470            
 471                // For each property:
 472            
 473                for (Uint32 i = 0, n = cimInstance.getPropertyCount(); i < n; i++)
 474                {
 475            	CIMConstProperty fromProp = cimInstance.getProperty(i);
 476            
 477            	// If a reference property:
 478            
 479            	if (fromProp.getType() == CIMType::REFERENCE)
 480            	{
 481            	    // For each property:
 482            
 483            	    for (Uint32 j = 0, n = cimInstance.getPropertyCount(); j < n; j++)
 484 mike  1.48 	    {
 485            		CIMConstProperty toProp = cimInstance.getProperty(j);
 486            
 487            		// If a reference property and not the same property:
 488            
 489            		if (toProp.getType() == CIMType::REFERENCE &&
 490            		    fromProp.getName() != toProp.getName())
 491            		{
 492            		    CIMReference fromRef;
 493            		    fromProp.getValue().get(fromRef);
 494            
 495            		    CIMReference toRef;
 496            		    toProp.getValue().get(toRef);
 497            
 498            		    String fromObjectName = fromRef.toString();
 499            		    String fromClassName = fromRef.getClassName();
 500            		    String fromPropertyName = fromProp.getName();
 501            		    String toObjectName = toRef.toString();
 502            		    String toClassName = toRef.getClassName();
 503            		    String toPropertyName = toProp.getName();
 504            
 505 mike  1.48 		    AssocInstTable::append(
 506            			os,
 507            			assocInstanceName,
 508            			assocClassName,
 509            			fromObjectName,
 510            			fromClassName,
 511            			fromPropertyName,
 512            			toObjectName,
 513            			toClassName,
 514            			toPropertyName);
 515            		}
 516            	    }
 517            	}
 518                }
 519            }
 520            
 521            void CIMRepository::createInstance(
 522                const String& nameSpace,
 523                const CIMInstance& newInstance)
 524            {
 525                // -- Resolve the instance (looks up class):
 526 mike  1.48 	CIMInstance cimInstance(newInstance);
 527            
 528                CIMConstClass cimClass;
 529                cimInstance.resolve(_context, nameSpace, cimClass);
 530                CIMReference instanceName = cimInstance.getInstanceName(cimClass);
 531            
 532                // -- Make sure the class has keys (otherwise it will be impossible to
 533                // -- create the instance.
 534            
 535                if (!cimClass.hasKeys())
 536                {
 537            	String message = "class has no keys: ";
 538            	message += cimClass.getClassName();
 539            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED, message);
 540                }
 541            
 542                // -- Be sure instance does not already exist:
 543            
 544                String className;
 545                Uint32 dummyIndex;
 546            
 547 mike  1.48     if (_getInstanceIndex(nameSpace, instanceName, className, dummyIndex, true))
 548                {
 549            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_ALREADY_EXISTS, instanceName.toString());
 550                }
 551            
 552                // -- Handle if association:
 553            
 554                if (cimClass.isAssociation())
 555                {
 556            	_createAssocInstEntries(nameSpace,
 557            	    cimClass, cimInstance, instanceName);
 558                }
 559            
 560                // -- Get common base (of instance file and index file):
 561            
 562                String instanceFileBase = _nameSpaceManager.getInstanceFileBase(
 563            	nameSpace, cimInstance.getClassName());
 564            
 565                // -- Make index file entry:
 566            
 567                String indexFilePath = _getIndexFilePath(
 568 mike  1.48 	nameSpace, cimInstance.getClassName());
 569                Uint32 index;
 570            
 571                if (!InstanceIndexFile::insert(indexFilePath, instanceName, index))
 572            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_ALREADY_EXISTS, instanceName.toString());
 573            
 574                // -- Save instance to file:
 575            
 576                String instanceFilePath = _getInstanceFilePath(nameSpace,
 577            	cimInstance.getClassName(), index);
 578            
 579                _SaveObject(instanceFilePath, cimInstance);
 580            }
 581            
 582            void CIMRepository::modifyClass(
 583                const String& nameSpace,
 584                const CIMClass& modifiedClass)
 585            {
 586                // -- Resolve the class:
 587            	CIMClass cimClass(modifiedClass);
 588            
 589 mike  1.48     cimClass.resolve(_context, nameSpace);
 590            
 591                // -- Check to see if it is okay to modify this class:
 592            
 593                String classFilePath;
 594            
 595                _nameSpaceManager.checkModify(nameSpace, cimClass.getClassName(),
 596            	cimClass.getSuperClassName(), classFilePath);
 597            
 598                // -- Delete the old file containing the class:
 599            
 600                if (!FileSystem::removeFileNoCase(classFilePath))
 601                {
 602            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
 603            	    "failed to remove file in CIMRepository::modifyClass()");
 604                }
 605            
 606                // -- Create new class file:
 607            
 608                _SaveObject(classFilePath, cimClass);
 609            }
 610 mike  1.48 
 611            void CIMRepository::modifyInstance(
 612                const String& nameSpace,
 613                const CIMInstance& modifiedInstance)
 614            {
 615                // -- Resolve the instance (looks up the class):
 616            	CIMInstance cimInstance(modifiedInstance);
 617            
 618                CIMConstClass cimClass;
 619                cimInstance.resolve(_context, nameSpace, cimClass);
 620            
 621                // -- Lookup index of entry from index file:
 622            
 623                CIMReference instanceName = cimInstance.getInstanceName(cimClass);
 624            
 625                String indexFilePath = _getIndexFilePath(
 626            	nameSpace, instanceName.getClassName());
 627            
 628                Uint32 index;
 629            
 630                if (!InstanceIndexFile::lookup(indexFilePath, instanceName, index))
 631 mike  1.48 	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_FOUND, instanceName.toString());
 632            
 633                // -- Attempt to remove the instance file:
 634            
 635                String instanceFilePath = _getInstanceFilePath(
 636            	nameSpace, instanceName.getClassName(), index);
 637            
 638                if (!FileSystem::removeFileNoCase(instanceFilePath))
 639                {
 640            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
 641            	    "failed to remove file in CIMRepository::deleteInstance()");
 642                }
 643            
 644                // -- Save instance to file:
 645            
 646                _SaveObject(instanceFilePath, cimInstance);
 647            }
 648            
 649            Array<CIMClass> CIMRepository::enumerateClasses(
 650                const String& nameSpace,
 651                const String& className,
 652 mike  1.48     Boolean deepInheritance,
 653                Boolean localOnly,
 654                Boolean includeQualifiers,
 655                Boolean includeClassOrigin)
 656            {
 657                Array<String> classNames;
 658            
 659                _nameSpaceManager.getSubClassNames(
 660            	nameSpace, className, deepInheritance, classNames);
 661            
 662                Array<CIMClass> result;
 663            
 664                for (Uint32 i = 0; i < classNames.size(); i++)
 665                {
 666            	result.append(getClass(nameSpace, classNames[i], localOnly,
 667            	    includeQualifiers, includeClassOrigin));
 668                }
 669            
 670                return result;
 671            }
 672            
 673 mike  1.48 Array<String> CIMRepository::enumerateClassNames(
 674                const String& nameSpace,
 675                const String& className,
 676                Boolean deepInheritance)
 677            {
 678                Array<String> classNames;
 679            
 680                _nameSpaceManager.getSubClassNames(
 681            	nameSpace, className, deepInheritance, classNames);
 682            
 683                return classNames;
 684                return Array<String>();
 685            }
 686            
 687            Array<CIMInstance> CIMRepository::enumerateInstances(
 688                const String& nameSpace,
 689                const String& className,
 690                Boolean deepInheritance,
 691                Boolean localOnly,
 692                Boolean includeQualifiers,
 693                Boolean includeClassOrigin,
 694 mike  1.48     const Array<String>& propertyList)
 695            {
 696                // -- Get all descendent classes of this class:
 697            
 698                Array<String> classNames;
 699                _nameSpaceManager.getSubClassNames(
 700            	nameSpace, className, true, classNames);
 701                classNames.prepend(className);
 702            
 703                // -- Search each qualifying instance file for the instance:
 704            
 705                Array<CIMReference> instanceNames;
 706                Array<Uint32> indices;
 707                Array<CIMInstance> instances;
 708                Uint32 start = 0;
 709            
 710                for (Uint32 i = 0; i < classNames.size(); i++)
 711                {
 712            	// -- Form the name of the class index file:
 713            
 714            	String path = _getIndexFilePath(nameSpace, classNames[i]);
 715 mike  1.48 
 716            	// Get all instance names for that class:
 717            
 718            	InstanceIndexFile::appendInstanceNamesTo(path, instanceNames, indices);
 719            	PEGASUS_ASSERT(instanceNames.size() == indices.size());
 720            
 721            	// -- Load up all the instances of this class:
 722            
 723            	for (Uint32 j = start; j < instanceNames.size(); j++)
 724            	{
 725            	    String instanceFilePath = _getInstanceFilePath(
 726            		nameSpace, classNames[i], indices[i]);
 727            
 728            	    CIMInstance tmpInstance;
 729            	    _LoadObject(instanceFilePath, tmpInstance);
 730            	    instances.append(tmpInstance);
 731            	}
 732            
 733            	start = instanceNames.size();
 734                }
 735            
 736 mike  1.48     return instances;
 737            }
 738            
 739            Array<CIMReference> CIMRepository::enumerateInstanceNames(
 740                const String& nameSpace,
 741                const String& className)
 742            {
 743                // -- Get all descendent classes of this class:
 744            
 745                Array<String> classNames;
 746                _nameSpaceManager.getSubClassNames(nameSpace, className, true, classNames);
 747                classNames.prepend(className);
 748            
 749                // -- Search each qualifying instance file for the instance:
 750            
 751                Array<CIMReference> instanceNames;
 752                Array<Uint32> indices;
 753            
 754                for (Uint32 i = 0; i < classNames.size(); i++)
 755                {
 756            	// -- Form the name of the class index file:
 757 mike  1.48 
 758            	String path = _getIndexFilePath(nameSpace, classNames[i]);
 759            
 760            	// Get all instances for that class:
 761            
 762            	InstanceIndexFile::appendInstanceNamesTo(path, instanceNames, indices);
 763                }
 764            
 765                return instanceNames;
 766            }
 767            
 768            Array<CIMInstance> CIMRepository::execQuery(
 769                const String& queryLanguage,
 770                const String& query)
 771            {
 772                throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_SUPPORTED, "execQuery()");
 773            
 774                return Array<CIMInstance>();
 775            }
 776            
 777            Array<CIMObjectWithPath> CIMRepository::associators(
 778 mike  1.48     const String& nameSpace,
 779                const CIMReference& objectName,
 780                const String& assocClass,
 781                const String& resultClass,
 782                const String& role,
 783                const String& resultRole,
 784                Boolean includeQualifiers,
 785                Boolean includeClassOrigin,
 786                const Array<String>& propertyList)
 787            {
 788                Array<CIMReference> names = associatorNames(
 789            	nameSpace,
 790            	objectName,
 791            	assocClass,
 792            	resultClass,
 793            	role,
 794            	resultRole);
 795            
 796                Array<CIMObjectWithPath> result;
 797            
 798                for (Uint32 i = 0, n = names.size(); i < n; i++)
 799 mike  1.48     {
 800            	String tmpNameSpace = names[i].getNameSpace();
 801            
 802            	if (tmpNameSpace.size() == 0)
 803            	    tmpNameSpace = nameSpace;
 804            
 805            	if (names[i].isClassName())
 806            	{
 807            	    CIMReference tmpRef = names[i];
 808            	    tmpRef.setHost(String());
 809            	    tmpRef.setNameSpace(String());
 810            
 811            	    CIMClass cimClass = getClass(
 812            		tmpNameSpace,
 813            		tmpRef.getClassName(),
 814            		false,
 815            		includeQualifiers,
 816            		includeClassOrigin,
 817            		propertyList);
 818            
 819            	    CIMObject cimObject(cimClass);
 820 mike  1.48 	    result.append(CIMObjectWithPath(names[i], cimObject));
 821            	}
 822            	else
 823            	{
 824            	    CIMReference tmpRef = names[i];
 825            	    tmpRef.setHost(String());
 826            	    tmpRef.setNameSpace(String());
 827            
 828            	    CIMInstance cimInstance = getInstance(
 829            		tmpNameSpace,
 830            		tmpRef,
 831            		false,
 832            		includeQualifiers,
 833            		includeClassOrigin,
 834            		propertyList);
 835            
 836            	    CIMObject cimObject(cimInstance);
 837            	    result.append(CIMObjectWithPath(names[i], cimObject));
 838            	}
 839                }
 840            
 841 mike  1.48     return result;
 842            }
 843            
 844            Array<CIMReference> CIMRepository::associatorNames(
 845                const String& nameSpace,
 846                const CIMReference& objectName,
 847                const String& assocClass,
 848                const String& resultClass,
 849                const String& role,
 850                const String& resultRole)
 851            {
 852                Array<String> associatorNames;
 853            
 854                if (objectName.isClassName())
 855                {
 856            	String assocFileName = _MakeAssocClassPath(nameSpace, _repositoryRoot);
 857            
 858            	AssocClassTable::getAssociatorNames(
 859            	    assocFileName,
 860            	    objectName.toString(),
 861            	    assocClass,
 862 mike  1.48 	    resultClass,
 863            	    role,
 864            	    resultRole,
 865            	    associatorNames);
 866                }
 867                else
 868                {
 869            	String assocFileName = _MakeAssocInstPath(nameSpace, _repositoryRoot);
 870            
 871            	AssocInstTable::getAssociatorNames(
 872            	    assocFileName,
 873            	    objectName.toString(),
 874            	    assocClass,
 875            	    resultClass,
 876            	    role,
 877            	    resultRole,
 878            	    associatorNames);
 879                }
 880            
 881                Array<CIMReference> result;
 882            
 883 mike  1.48     for (Uint32 i = 0, n = associatorNames.size(); i < n; i++)
 884                {
 885            	CIMReference r = associatorNames[i];
 886            
 887                    if (r.getHost().size() == 0)
 888                        r.setHost(System::getHostName());
 889            
 890                    if (r.getNameSpace().size() == 0)
 891                        r.setNameSpace(nameSpace);
 892            
 893            	result.append(r);
 894                }
 895            
 896                return result;
 897            }
 898            
 899            Array<CIMObjectWithPath> CIMRepository::references(
 900                const String& nameSpace,
 901                const CIMReference& objectName,
 902                const String& resultClass,
 903                const String& role,
 904 mike  1.48     Boolean includeQualifiers,
 905                Boolean includeClassOrigin,
 906                const Array<String>& propertyList)
 907            {
 908                Array<CIMReference> names = referenceNames(
 909            	nameSpace,
 910            	objectName,
 911            	resultClass,
 912            	role);
 913            
 914                Array<CIMObjectWithPath> result;
 915            
 916                for (Uint32 i = 0, n = names.size(); i < n; i++)
 917                {
 918            	String tmpNameSpace = names[i].getNameSpace();
 919            
 920            	if (tmpNameSpace.size() == 0)
 921            	    tmpNameSpace = nameSpace;
 922            
 923            	// ATTN: getInstance() should this be able to handle instance names
 924            	// with host names and namespaces?
 925 mike  1.48 
 926            	CIMReference tmpRef = names[i];
 927            	tmpRef.setHost(String());
 928            	tmpRef.setNameSpace(String());
 929            
 930            	if (objectName.isClassName())
 931            	{
 932            	    CIMClass cimClass = getClass(
 933            		tmpNameSpace,
 934            		tmpRef.getClassName(),
 935            		false,
 936            		includeQualifiers,
 937            		includeClassOrigin,
 938            		propertyList);
 939            
 940            	    result.append(CIMObjectWithPath(names[i], cimClass));
 941            	}
 942            	else
 943            	{
 944            	    CIMInstance instance = getInstance(
 945            		tmpNameSpace,
 946 mike  1.48 		tmpRef,
 947            		false,
 948            		includeQualifiers,
 949            		includeClassOrigin,
 950            		propertyList);
 951            
 952            	    result.append(CIMObjectWithPath(names[i], instance));
 953            	}
 954                }
 955            
 956                return result;
 957            }
 958            
 959            Array<CIMReference> CIMRepository::referenceNames(
 960                const String& nameSpace,
 961                const CIMReference& objectName,
 962                const String& resultClass,
 963                const String& role)
 964            {
 965                Array<String> tmpReferenceNames;
 966            
 967 mike  1.48     if (objectName.isClassName())
 968                {
 969            	String assocFileName = _MakeAssocClassPath(nameSpace, _repositoryRoot);
 970            
 971            	if (!AssocClassTable::getReferenceNames(
 972            	    assocFileName,
 973            	    objectName.getClassName(),
 974            	    resultClass,
 975            	    role,
 976            	    tmpReferenceNames))
 977            	{
 978            	    // Ignore error! It's okay not to have references.
 979            	}
 980                }
 981                else
 982                {
 983            	String assocFileName = _MakeAssocInstPath(nameSpace, _repositoryRoot);
 984            
 985            	if (!AssocInstTable::getReferenceNames(
 986            	    assocFileName,
 987            	    objectName,
 988 mike  1.48 	    resultClass,
 989            	    role,
 990            	    tmpReferenceNames))
 991            	{
 992            	    // Ignore error! It's okay not to have references.
 993            	}
 994                }
 995            
 996                Array<CIMReference> result;
 997            
 998                for (Uint32 i = 0, n = tmpReferenceNames.size(); i < n; i++)
 999                {
1000            	CIMReference r = tmpReferenceNames[i];
1001            
1002                    if (r.getHost().size() == 0)
1003                        r.setHost(System::getHostName());
1004            
1005                    if (r.getNameSpace().size() == 0)
1006                        r.setNameSpace(nameSpace);
1007            
1008            	result.append(r);
1009 mike  1.48     }
1010            
1011                return result;
1012            }
1013            
1014            CIMValue CIMRepository::getProperty(
1015                const String& nameSpace,
1016                const CIMReference& instanceName,
1017                const String& propertyName)
1018            {
1019                // -- Get the index for this instance:
1020            
1021                String className;
1022                Uint32 index;
1023            
1024                if (!_getInstanceIndex(nameSpace, instanceName, className, index))
1025            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_FOUND, "getProperty()");
1026            
1027                // -- Load the instance into memory:
1028            
1029                String path = _getInstanceFilePath(nameSpace, className, index);
1030 mike  1.48     CIMInstance cimInstance;
1031                _LoadObject(path, cimInstance);
1032            
1033                // -- Grab the property from the instance:
1034            
1035                Uint32 pos = cimInstance.findProperty(propertyName);
1036            
1037                if (pos == PEGASUS_NOT_FOUND)
1038            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NO_SUCH_PROPERTY, "getProperty()");
1039            
1040                CIMProperty prop = cimInstance.getProperty(pos);
1041            
1042                // -- Return the value:
1043            
1044                return prop.getValue();
1045            }
1046            
1047            void CIMRepository::setProperty(
1048                const String& nameSpace,
1049                const CIMReference& instanceName,
1050                const String& propertyName,
1051 mike  1.48     const CIMValue& newValue)
1052            {
1053                // -- Load the instance:
1054            
1055                CIMInstance instance = getInstance(
1056            	nameSpace, instanceName, false, true);
1057            
1058                // -- Get the class:
1059            
1060                CIMClass cimClass = getClass(nameSpace, instance.getClassName(),
1061            	false, true);
1062            
1063                // -- Save instance name:
1064            
1065                CIMReference oldRef = instance.getInstanceName(cimClass);
1066            
1067                // -- Modify the property (disallow if property is a key):
1068            
1069                Uint32 pos = instance.findProperty(propertyName);
1070            
1071                if (pos == PEGASUS_NOT_FOUND)
1072 mike  1.48 	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NO_SUCH_PROPERTY, "setProperty()");
1073            
1074                CIMProperty prop = instance.getProperty(pos);
1075            
1076                prop.setValue(newValue);
1077            
1078                // -- Disallow if instance name is changed by this operation (attempt
1079                // -- to modify a key property.
1080            
1081                CIMReference newRef = instance.getInstanceName(cimClass);
1082            
1083                if (oldRef != newRef)
1084                {
1085            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
1086            	    "setProperty(): attempted to modify a key property");
1087                }
1088            
1089                // -- Modify the instance:
1090            
1091                modifyInstance(nameSpace, instance);
1092            }
1093 mike  1.48 
1094            CIMQualifierDecl CIMRepository::getQualifier(
1095                const String& nameSpace,
1096                const String& qualifierName)
1097            {
1098                // -- Get path of qualifier file:
1099            
1100                String qualifierFilePath = _nameSpaceManager.getQualifierFilePath(
1101            	nameSpace, qualifierName);
1102            
1103                // -- Load qualifier:
1104            
1105                CIMQualifierDecl qualifierDecl;
1106            
1107                try
1108                {
1109            	_LoadObject(qualifierFilePath, qualifierDecl);
1110                }
1111                catch (CannotOpenFile&)
1112                {
1113            	return CIMQualifierDecl();
1114 mike  1.48     }
1115            
1116                return qualifierDecl;
1117            }
1118            
1119            void CIMRepository::setQualifier(
1120                const String& nameSpace,
1121                const CIMQualifierDecl& qualifierDecl)
1122            {
1123                // -- Get path of qualifier file:
1124            
1125                String qualifierFilePath = _nameSpaceManager.getQualifierFilePath(
1126            	nameSpace, qualifierDecl.getName());
1127            
1128                // -- If qualifier alread exists, throw exception:
1129            
1130                if (FileSystem::existsNoCase(qualifierFilePath))
1131            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_ALREADY_EXISTS, qualifierDecl.getName());
1132            
1133                // -- Save qualifier:
1134            
1135 mike  1.48     _SaveObject(qualifierFilePath, qualifierDecl);
1136            }
1137            
1138            void CIMRepository::deleteQualifier(
1139                const String& nameSpace,
1140                const String& qualifierName)
1141            {
1142                // -- Get path of qualifier file:
1143            
1144                String qualifierFilePath = _nameSpaceManager.getQualifierFilePath(
1145            	nameSpace, qualifierName);
1146            
1147                // -- Delete qualifier:
1148            
1149                if (!FileSystem::removeFileNoCase(qualifierFilePath))
1150            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_FOUND, qualifierName);
1151            }
1152            
1153            Array<CIMQualifierDecl> CIMRepository::enumerateQualifiers(
1154                const String& nameSpace)
1155            {
1156 mike  1.48     String qualifiersRoot = _nameSpaceManager.getQualifiersRoot(nameSpace);
1157            
1158                Array<String> qualifierNames;
1159            
1160                if (!FileSystem::getDirectoryContents(qualifiersRoot, qualifierNames))
1161                {
1162            	throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED,
1163            	    "enumerateQualifiers(): internal error");
1164                }
1165            
1166                Array<CIMQualifierDecl> qualifiers;
1167            
1168                for (Uint32 i = 0; i < qualifierNames.size(); i++)
1169                {
1170            	CIMQualifierDecl qualifier = getQualifier(nameSpace, qualifierNames[i]);
1171            	qualifiers.append(qualifier);
1172                }
1173            
1174                return qualifiers;
1175            }
1176            
1177 mike  1.48 CIMValue CIMRepository::invokeMethod(
1178                const String& nameSpace,
1179                const CIMReference& instanceName,
1180                const String& methodName,
1181                const Array<CIMValue>& inParameters,
1182                Array<CIMValue>& outParameters)
1183            {
1184                throw PEGASUS_CIM_EXCEPTION(CIM_ERR_NOT_SUPPORTED, "invokeMethod()");
1185                return CIMValue();
1186            }
1187            
1188            void CIMRepository::createNameSpace(const String& nameSpace)
1189            {
1190                _nameSpaceManager.createNameSpace(nameSpace);
1191            }
1192            
1193            Array<String> CIMRepository::enumerateNameSpaces() const
1194            {
1195                Array<String> nameSpaceNames;
1196                _nameSpaceManager.getNameSpaceNames(nameSpaceNames);
1197                return nameSpaceNames;
1198 mike  1.48 }
1199            
1200            void CIMRepository::deleteNameSpace(const String& nameSpace)
1201            {
1202                _nameSpaceManager.deleteNameSpace(nameSpace);
1203            }
1204            
1205            String CIMRepository::_getIndexFilePath(
1206                const String& nameSpace,
1207                const String& className) const
1208            {
1209                String tmp = _nameSpaceManager.getInstanceFileBase(nameSpace, className);
1210                tmp.append(".idx");
1211                return tmp;
1212            }
1213            
1214            String CIMRepository::_getInstanceFilePath(
1215                const String& nameSpace,
1216                const String& className,
1217                Uint32 index) const
1218            {
1219 mike  1.48     String tmp = _nameSpaceManager.getInstanceFileBase(nameSpace, className);
1220                char extension[32];
1221                sprintf(extension, ".%d", index);
1222                tmp += extension;
1223                return tmp;
1224            }
1225            
1226 bob   1.49 void CIMRepository::setDeclContext(RepositoryDeclContext *context)
1227            {
1228              _context = context;
1229            }
1230            
1231 mike  1.48 PEGASUS_NAMESPACE_END

No CVS admin address has been configured
Powered by
ViewCVS 0.9.2