<commit_before>// Copyright 2012 Cloudera Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "exprs/tuple-is-null-predicate.h"

#include <sstream>

#include "gen-cpp/Exprs_types.h"

using namespace std;

namespace impala {

BooleanVal TupleIsNullPredicate::GetBooleanVal(ExprContext* ctx, TupleRow* row) {
  bool result = true;
  for (int i = 0; i < tuple_idxs_.size(); ++i) {
    if (row->GetTuple(tuple_idxs_[i]) != NULL) {
      result = false;
      break;
    }
  }
  return BooleanVal(result);
}

TupleIsNullPredicate::TupleIsNullPredicate(const TExprNode& node)
  : Predicate(node),
    tuple_ids_(node.tuple_is_null_pred.tuple_ids.begin(),
               node.tuple_is_null_pred.tuple_ids.end()) {
}

Status TupleIsNullPredicate::Prepare(RuntimeState* state, const RowDescriptor& row_desc,
                                     ExprContext* ctx) {
  RETURN_IF_ERROR(Expr::Prepare(state, row_desc, ctx));
  DCHECK_EQ(0, children_.size());
  // Resolve tuple ids to tuple indexes.
  for (int i = 0; i < tuple_ids_.size(); ++i) {
    int32_t tuple_idx = row_desc.GetTupleIdx(tuple_ids_[i]);
    DCHECK_NE(RowDescriptor::INVALID_IDX, tuple_idx);
    if (row_desc.TupleIsNullable(tuple_idx)) tuple_idxs_.push_back(tuple_idx);
  }
  return Status::OK;
}

Status TupleIsNullPredicate::GetCodegendComputeFn(RuntimeState* state,
                                                  llvm::Function** fn) {
  return GetCodegendComputeFnWrapper(state, fn);
}

string TupleIsNullPredicate::DebugString() const {
  stringstream out;
  out << "TupleIsNullPredicate(tupleids=[";
  for (int i = 0; i < tuple_ids_.size(); ++i) {
    out << (i == 0 ? "" : " ") << tuple_ids_[i];
  }
  out << "])";
  return out.str();
}

}
<commit_msg>Update TupleIsNullPredicate to not crash in case of bad plans.<commit_after>// Copyright 2012 Cloudera Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "exprs/tuple-is-null-predicate.h"

#include <sstream>

#include "gen-cpp/Exprs_types.h"

using namespace std;

namespace impala {

BooleanVal TupleIsNullPredicate::GetBooleanVal(ExprContext* ctx, TupleRow* row) {
  bool result = true;
  for (int i = 0; i < tuple_idxs_.size(); ++i) {
    if (row->GetTuple(tuple_idxs_[i]) != NULL) {
      result = false;
      break;
    }
  }
  return BooleanVal(result);
}

TupleIsNullPredicate::TupleIsNullPredicate(const TExprNode& node)
  : Predicate(node),
    tuple_ids_(node.tuple_is_null_pred.tuple_ids.begin(),
               node.tuple_is_null_pred.tuple_ids.end()) {
}

Status TupleIsNullPredicate::Prepare(RuntimeState* state, const RowDescriptor& row_desc,
                                     ExprContext* ctx) {
  RETURN_IF_ERROR(Expr::Prepare(state, row_desc, ctx));
  DCHECK_EQ(0, children_.size());
  // Resolve tuple ids to tuple indexes.
  for (int i = 0; i < tuple_ids_.size(); ++i) {
    int32_t tuple_idx = row_desc.GetTupleIdx(tuple_ids_[i]);
    if (tuple_idx == RowDescriptor::INVALID_IDX) {
      // This should not happen and indicates a planner issue. This code is tricky
      // so rather than crashing, do this as a stop gap.
      // TODO: remove this code and replace with DCHECK.
      return Status("Invalid plan. TupleIsNullPredicate has invalid tuple idx.");
    }
    if (row_desc.TupleIsNullable(tuple_idx)) tuple_idxs_.push_back(tuple_idx);
  }
  return Status::OK;
}

Status TupleIsNullPredicate::GetCodegendComputeFn(RuntimeState* state,
                                                  llvm::Function** fn) {
  return GetCodegendComputeFnWrapper(state, fn);
}

string TupleIsNullPredicate::DebugString() const {
  stringstream out;
  out << "TupleIsNullPredicate(tupleids=[";
  for (int i = 0; i < tuple_ids_.size(); ++i) {
    out << (i == 0 ? "" : " ") << tuple_ids_[i];
  }
  out << "])";
  return out.str();
}

}
<|endoftext|>


<commit_before>// Copyright 2014 The Bazel Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//    http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "src/main/native/unix_jni.h"

#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/sysctl.h>
#include <sys/syslimits.h>
#include <sys/types.h>

#include <string>

const int PATH_MAX2 = PATH_MAX * 2;

using std::string;

// See unix_jni.h.
string ErrorMessage(int error_number) {
  char buf[1024] = "";
  if (strerror_r(error_number, buf, sizeof buf) < 0) {
    snprintf(buf, sizeof buf, "strerror_r(%d): errno %d", error_number, errno);
  }

  return string(buf);
}

int portable_fstatat(
    int dirfd, char *name, portable_stat_struct *statbuf, int flags) {
  char dirPath[PATH_MAX2];  // Have enough room for relative path

  // No fstatat under darwin, simulate it
  if (flags != 0) {
    // We don't support any flags
    errno = ENOSYS;
    return -1;
  }
  if (strlen(name) == 0 || name[0] == '/') {
    // Absolute path, simply stat
    return portable_stat(name, statbuf);
  }
  // Relative path, construct an absolute path
  if (fcntl(dirfd, F_GETPATH, dirPath) == -1) {
    return -1;
  }
  int l = strlen(dirPath);
  if (dirPath[l-1] != '/') {
    // dirPath is twice the PATH_MAX size, we always have room for the extra /
    dirPath[l] = '/';
    dirPath[l+1] = 0;
    l++;
  }
  strncat(dirPath, name, PATH_MAX2-l-1);
  char *newpath = realpath(dirPath, NULL);  // this resolve the relative path
  if (newpath == NULL) {
    return -1;
  }
  int r = portable_stat(newpath, statbuf);
  free(newpath);
  return r;
}

int StatSeconds(const portable_stat_struct &statbuf, StatTimes t) {
  switch (t) {
    case STAT_ATIME:
      return statbuf.st_atime;
    case STAT_CTIME:
      return statbuf.st_ctime;
    case STAT_MTIME:
      return statbuf.st_mtime;
    default:
      CHECK(false);
  }
}

int StatNanoSeconds(const portable_stat_struct &statbuf, StatTimes t) {
  switch (t) {
    case STAT_ATIME:
      return statbuf.st_atimespec.tv_nsec;
    case STAT_CTIME:
      return statbuf.st_ctimespec.tv_nsec;
    case STAT_MTIME:
      return statbuf.st_mtimespec.tv_nsec;
    default:
      CHECK(false);
  }
}

ssize_t portable_getxattr(const char *path, const char *name, void *value,
                          size_t size) {
  errno = ENOSYS;
  return -1;
}

ssize_t portable_lgetxattr(const char *path, const char *name, void *value,
                           size_t size) {
  errno = ENOSYS;
  return -1;
}

int portable_sysctlbyname(const char *name_chars, long *mibp, size_t *sizep) {
  return sysctlbyname(name_chars, mibp, sizep, NULL, 0);
}
<commit_msg>Add support for xattr to Darwin.<commit_after>// Copyright 2014 The Bazel Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//    http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "src/main/native/unix_jni.h"

#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/sysctl.h>
#include <sys/syslimits.h>
#include <sys/types.h>
#include <sys/xattr.h>

#include <string>

const int PATH_MAX2 = PATH_MAX * 2;

using std::string;

// See unix_jni.h.
string ErrorMessage(int error_number) {
  char buf[1024] = "";
  if (strerror_r(error_number, buf, sizeof buf) < 0) {
    snprintf(buf, sizeof buf, "strerror_r(%d): errno %d", error_number, errno);
  }

  return string(buf);
}

int portable_fstatat(
    int dirfd, char *name, portable_stat_struct *statbuf, int flags) {
  char dirPath[PATH_MAX2];  // Have enough room for relative path

  // No fstatat under darwin, simulate it
  if (flags != 0) {
    // We don't support any flags
    errno = ENOSYS;
    return -1;
  }
  if (strlen(name) == 0 || name[0] == '/') {
    // Absolute path, simply stat
    return portable_stat(name, statbuf);
  }
  // Relative path, construct an absolute path
  if (fcntl(dirfd, F_GETPATH, dirPath) == -1) {
    return -1;
  }
  int l = strlen(dirPath);
  if (dirPath[l-1] != '/') {
    // dirPath is twice the PATH_MAX size, we always have room for the extra /
    dirPath[l] = '/';
    dirPath[l+1] = 0;
    l++;
  }
  strncat(dirPath, name, PATH_MAX2-l-1);
  char *newpath = realpath(dirPath, NULL);  // this resolve the relative path
  if (newpath == NULL) {
    return -1;
  }
  int r = portable_stat(newpath, statbuf);
  free(newpath);
  return r;
}

int StatSeconds(const portable_stat_struct &statbuf, StatTimes t) {
  switch (t) {
    case STAT_ATIME:
      return statbuf.st_atime;
    case STAT_CTIME:
      return statbuf.st_ctime;
    case STAT_MTIME:
      return statbuf.st_mtime;
    default:
      CHECK(false);
  }
}

int StatNanoSeconds(const portable_stat_struct &statbuf, StatTimes t) {
  switch (t) {
    case STAT_ATIME:
      return statbuf.st_atimespec.tv_nsec;
    case STAT_CTIME:
      return statbuf.st_ctimespec.tv_nsec;
    case STAT_MTIME:
      return statbuf.st_mtimespec.tv_nsec;
    default:
      CHECK(false);
  }
}

ssize_t portable_getxattr(const char *path, const char *name, void *value,
                          size_t size) {
  return getxattr(path, name, value, size, 0, 0);
}

ssize_t portable_lgetxattr(const char *path, const char *name, void *value,
                           size_t size) {
  return getxattr(path, name, value, size, 0, XATTR_NOFOLLOW);
}

int portable_sysctlbyname(const char *name_chars, long *mibp, size_t *sizep) {
  return sysctlbyname(name_chars, mibp, sizep, NULL, 0);
}
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: xmlTableFilterList.cxx,v $
 *
 *  $Revision: 1.10 $
 *
 *  last change: $Author: rt $ $Date: 2007-11-09 08:18:39 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_dbaccess.hxx"
#ifndef DBA_XMLTABLEFILTERLIST_HXX
#include "xmlTableFilterList.hxx"
#endif
#ifndef DBA_XMLTABLEFILTERPATTERN_HXX
#include "xmlTableFilterPattern.hxx"
#endif
#ifndef DBA_XMLENUMS_HXX
#include "xmlEnums.hxx"
#endif
#ifndef _XMLOFF_XMLTOKEN_HXX
#include <xmloff/xmltoken.hxx>
#endif
#ifndef _XMLOFF_XMLNMSPE_HXX
#include <xmloff/xmlnmspe.hxx>
#endif
#ifndef _XMLOFF_NMSPMAP_HXX
#include <xmloff/nmspmap.hxx>
#endif
#ifndef _XMLOFF_XMLTOKEN_HXX
#include <xmloff/xmltoken.hxx>
#endif
#ifndef DBACCESS_SHARED_XMLSTRINGS_HRC
#include "xmlstrings.hrc"
#endif
#ifndef _COM_SUN_STAR_BEANS_XPROPERTYSET_HPP_
#include <com/sun/star/beans/XPropertySet.hpp>
#endif
#ifndef _XMLOFF_XMLIMP_HXX
#include <xmloff/xmlimp.hxx>
#endif
#ifndef DBA_XMLFILTER_HXX
#include "xmlfilter.hxx"
#endif
#ifndef _TOOLS_DEBUG_HXX
#include <tools/debug.hxx>
#endif

namespace dbaxml
{
    using namespace ::xmloff::token;
    using namespace ::com::sun::star::uno;
    using namespace ::com::sun::star::beans;
    using namespace ::com::sun::star::xml::sax;
DBG_NAME(OXMLTableFilterList)

OXMLTableFilterList::OXMLTableFilterList( SvXMLImport& rImport, sal_uInt16 nPrfx, const ::rtl::OUString& _sLocalName )
    :SvXMLImportContext( rImport, nPrfx, _sLocalName )
{
    DBG_CTOR(OXMLTableFilterList,NULL);

}
// -----------------------------------------------------------------------------

OXMLTableFilterList::~OXMLTableFilterList()
{
    DBG_DTOR(OXMLTableFilterList,NULL);
}
// -----------------------------------------------------------------------------

SvXMLImportContext* OXMLTableFilterList::CreateChildContext(
        sal_uInt16 nPrefix,
        const ::rtl::OUString& rLocalName,
        const Reference< XAttributeList > & /*xAttrList*/ )
{
    SvXMLImportContext *pContext = 0;

    if ( XML_NAMESPACE_DB == nPrefix )
    {
        GetImport().GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
        if ( IsXMLToken( rLocalName, XML_TABLE_FILTER_PATTERN ) )
            pContext = new OXMLTableFilterPattern( GetImport(), nPrefix, rLocalName,sal_True,*this);
        else if ( IsXMLToken( rLocalName, XML_TABLE_TYPE ) )
            pContext = new OXMLTableFilterPattern( GetImport(), nPrefix, rLocalName,sal_False,*this);
        else if ( IsXMLToken( rLocalName, XML_TABLE_INCLUDE_FILTER ) )
            pContext = new OXMLTableFilterList( GetImport(), nPrefix, rLocalName );
    }

    if( !pContext )
        pContext = new SvXMLImportContext( GetImport(), nPrefix, rLocalName );

    return pContext;
}
// -----------------------------------------------------------------------------
ODBFilter& OXMLTableFilterList::GetOwnImport()
{
    return static_cast<ODBFilter&>(GetImport());
}

// -----------------------------------------------------------------------------
void OXMLTableFilterList::EndElement()
{
    Reference<XPropertySet> xDataSource(GetOwnImport().getDataSource());
    if ( xDataSource.is() )
    {
        if ( !m_aPatterns.empty() )
            xDataSource->setPropertyValue(PROPERTY_TABLEFILTER,makeAny(Sequence< ::rtl::OUString>(&(*m_aPatterns.begin()),m_aPatterns.size())));
        if ( !m_aTypes.empty() )
            xDataSource->setPropertyValue(PROPERTY_TABLETYPEFILTER,makeAny(Sequence< ::rtl::OUString>(&(*m_aTypes.begin()),m_aTypes.size())));
    }
}
//----------------------------------------------------------------------------
} // namespace dbaxml
// -----------------------------------------------------------------------------
<commit_msg>INTEGRATION: CWS changefileheader (1.10.84); FILE MERGED 2008/03/31 13:26:56 rt 1.10.84.1: #i87441# Change license header to LPGL v3.<commit_after>/*************************************************************************
 *
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * Copyright 2008 by Sun Microsystems, Inc.
 *
 * OpenOffice.org - a multi-platform office productivity suite
 *
 * $RCSfile: xmlTableFilterList.cxx,v $
 * $Revision: 1.11 $
 *
 * This file is part of OpenOffice.org.
 *
 * OpenOffice.org is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License version 3
 * only, as published by the Free Software Foundation.
 *
 * OpenOffice.org is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License version 3 for more details
 * (a copy is included in the LICENSE file that accompanied this code).
 *
 * You should have received a copy of the GNU Lesser General Public License
 * version 3 along with OpenOffice.org.  If not, see
 * <http://www.openoffice.org/license.html>
 * for a copy of the LGPLv3 License.
 *
 ************************************************************************/

// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_dbaccess.hxx"
#ifndef DBA_XMLTABLEFILTERLIST_HXX
#include "xmlTableFilterList.hxx"
#endif
#ifndef DBA_XMLTABLEFILTERPATTERN_HXX
#include "xmlTableFilterPattern.hxx"
#endif
#ifndef DBA_XMLENUMS_HXX
#include "xmlEnums.hxx"
#endif
#ifndef _XMLOFF_XMLTOKEN_HXX
#include <xmloff/xmltoken.hxx>
#endif
#ifndef _XMLOFF_XMLNMSPE_HXX
#include <xmloff/xmlnmspe.hxx>
#endif
#ifndef _XMLOFF_NMSPMAP_HXX
#include <xmloff/nmspmap.hxx>
#endif
#ifndef _XMLOFF_XMLTOKEN_HXX
#include <xmloff/xmltoken.hxx>
#endif
#ifndef DBACCESS_SHARED_XMLSTRINGS_HRC
#include "xmlstrings.hrc"
#endif
#ifndef _COM_SUN_STAR_BEANS_XPROPERTYSET_HPP_
#include <com/sun/star/beans/XPropertySet.hpp>
#endif
#ifndef _XMLOFF_XMLIMP_HXX
#include <xmloff/xmlimp.hxx>
#endif
#ifndef DBA_XMLFILTER_HXX
#include "xmlfilter.hxx"
#endif
#ifndef _TOOLS_DEBUG_HXX
#include <tools/debug.hxx>
#endif

namespace dbaxml
{
    using namespace ::xmloff::token;
    using namespace ::com::sun::star::uno;
    using namespace ::com::sun::star::beans;
    using namespace ::com::sun::star::xml::sax;
DBG_NAME(OXMLTableFilterList)

OXMLTableFilterList::OXMLTableFilterList( SvXMLImport& rImport, sal_uInt16 nPrfx, const ::rtl::OUString& _sLocalName )
    :SvXMLImportContext( rImport, nPrfx, _sLocalName )
{
    DBG_CTOR(OXMLTableFilterList,NULL);

}
// -----------------------------------------------------------------------------

OXMLTableFilterList::~OXMLTableFilterList()
{
    DBG_DTOR(OXMLTableFilterList,NULL);
}
// -----------------------------------------------------------------------------

SvXMLImportContext* OXMLTableFilterList::CreateChildContext(
        sal_uInt16 nPrefix,
        const ::rtl::OUString& rLocalName,
        const Reference< XAttributeList > & /*xAttrList*/ )
{
    SvXMLImportContext *pContext = 0;

    if ( XML_NAMESPACE_DB == nPrefix )
    {
        GetImport().GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
        if ( IsXMLToken( rLocalName, XML_TABLE_FILTER_PATTERN ) )
            pContext = new OXMLTableFilterPattern( GetImport(), nPrefix, rLocalName,sal_True,*this);
        else if ( IsXMLToken( rLocalName, XML_TABLE_TYPE ) )
            pContext = new OXMLTableFilterPattern( GetImport(), nPrefix, rLocalName,sal_False,*this);
        else if ( IsXMLToken( rLocalName, XML_TABLE_INCLUDE_FILTER ) )
            pContext = new OXMLTableFilterList( GetImport(), nPrefix, rLocalName );
    }

    if( !pContext )
        pContext = new SvXMLImportContext( GetImport(), nPrefix, rLocalName );

    return pContext;
}
// -----------------------------------------------------------------------------
ODBFilter& OXMLTableFilterList::GetOwnImport()
{
    return static_cast<ODBFilter&>(GetImport());
}

// -----------------------------------------------------------------------------
void OXMLTableFilterList::EndElement()
{
    Reference<XPropertySet> xDataSource(GetOwnImport().getDataSource());
    if ( xDataSource.is() )
    {
        if ( !m_aPatterns.empty() )
            xDataSource->setPropertyValue(PROPERTY_TABLEFILTER,makeAny(Sequence< ::rtl::OUString>(&(*m_aPatterns.begin()),m_aPatterns.size())));
        if ( !m_aTypes.empty() )
            xDataSource->setPropertyValue(PROPERTY_TABLETYPEFILTER,makeAny(Sequence< ::rtl::OUString>(&(*m_aTypes.begin()),m_aTypes.size())));
    }
}
//----------------------------------------------------------------------------
} // namespace dbaxml
// -----------------------------------------------------------------------------
<|endoftext|>


<commit_before>//---------------------------------------------------------------------------
//    $Id$
//    Version: $Name$
//
//    Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005 by the deal.II authors
//
//    This file is subject to QPL and may not be  distributed
//    without copyright and license information. Please refer
//    to the file deal.II/doc/license.html for the  text  and
//    further information on this license.
//
//---------------------------------------------------------------------------

#include <base/quadrature_lib.h>
#include <base/thread_management.h>
#include <lac/vector.h>
#include <lac/block_vector.h>
#include <numerics/data_out_faces.h>
#include <grid/tria.h>
#include <dofs/dof_handler.h>
#include <dofs/dof_accessor.h>
#include <grid/tria_iterator.h>
#include <fe/fe.h>
#include <fe/fe_values.h>
#include <fe/hp_fe_values.h>
#include <fe/select_fe_values.h>
#include <fe/mapping_q1.h>

template <int dim, template <int> class DH>
void DataOutFaces<dim,DH>::build_some_patches (Data data)
{
  QTrapez<1>        q_trapez;
  QIterated<dim-1>  patch_points (q_trapez, data.n_subdivisions);

				   // since most output formats can't
				   // handle cells that are not
				   // transformed using a Q1 mapping,
				   // we don't support anything else
				   // as well
  static const MappingQ1<dim> mapping;
  typename SelectFEValues<DH<dim> >::FEFaceValues
    x_fe_patch_values (mapping, this->dofs->get_fe(),
                       patch_points, update_values);

  const unsigned int n_q_points = patch_points.n_quadrature_points;

  typename std::vector< ::DataOutBase::Patch<dim-1,dim> >::iterator patch = this->patches.begin();
  FaceDescriptor face=first_face();

				   // get first face in this thread
  for (unsigned int i=0; (i<data.this_thread)&&(face.first != this->dofs->end()); ++i)
    {
      ++patch;
      face=next_face(face);
    }

  				   // now loop over all cells and
				   // actually create the patches
  for (; face.first != this->dofs->end();)
    {
      Assert (patch != this->patches.end(), ExcInternalError());

      for (unsigned int vertex=0; vertex<GeometryInfo<dim-1>::vertices_per_cell; ++vertex)
	patch->vertices[vertex] = face.first->face(face.second)->vertex(vertex);

      if (data.n_datasets > 0)
	{
	  x_fe_patch_values.reinit (face.first, face.second);
          const FEFaceValues<dim> &fe_patch_values
            = x_fe_patch_values.get_present_fe_values ();

					   // first fill dof_data
	  for (unsigned int dataset=0; dataset<this->dof_data.size(); ++dataset)
	    {
	      if (data.n_components == 1)
		{
                  this->dof_data[dataset]->get_function_values (fe_patch_values,
                                                                data.patch_values);

		  for (unsigned int q=0; q<n_q_points; ++q)
		    patch->data(dataset,q) = data.patch_values[q];
		}
	      else
						 // system of components
		{
                  this->dof_data[dataset]->get_function_values (fe_patch_values,
                                                                data.patch_values_system);

		  for (unsigned int component=0; component<data.n_components;
		       ++component)
		    for (unsigned int q=0; q<n_q_points; ++q)
		      patch->data(dataset*data.n_components+component,q) =
			data.patch_values_system[q](component);
		};
	    };

					   // then do the cell data
	  for (unsigned int dataset=0; dataset<this->cell_data.size(); ++dataset)
	    {
					       // we need to get at
					       // the number of the
					       // cell to which this
					       // face belongs in
					       // order to access the
					       // cell data. this is
					       // not readily
					       // available, so choose
					       // the following rather
					       // inefficient way:
	      Assert (face.first->active(), ExcCellNotActiveForCellData());
	      const unsigned int cell_number
		= std::distance (this->dofs->begin_active(),
				 typename DH<dim>::active_cell_iterator(face.first));

              const double value
                = this->cell_data[dataset]->get_cell_data_value (cell_number);
              for (unsigned int q=0; q<n_q_points; ++q)
                patch->data(dataset+this->dof_data.size()*data.n_components,q) =
                  value;
	    };
	};
      				       // next cell (patch) in this thread
      for (unsigned int i=0;
	   (i<data.n_threads)&&(face.first != this->dofs->end()); ++i)
	{
	  ++patch;
	  face=next_face(face);
	}
    };
}

template <int dim, template <int> class DH>
void DataOutFaces<dim,DH>::build_patches (const unsigned int n_subdivisions,
					  const unsigned int n_threads_)
{
  Assert (n_subdivisions >= 1,
	  ExcInvalidNumberOfSubdivisions(n_subdivisions));

  typedef DataOut_DoFData<dim,DH,dim+1> BaseClass;
  Assert (this->dofs != 0, typename BaseClass::ExcNoDoFHandlerSelected());

  const unsigned int n_threads = (DEAL_II_USE_MT ? n_threads_ : 1);

				   // before we start the loop:
				   // create a quadrature rule that
				   // actually has the points on this
				   // patch
  QTrapez<1>       q_trapez;
  QIterated<dim-1> patch_points (q_trapez, n_subdivisions);

  const unsigned int n_q_points     = patch_points.n_quadrature_points;
  const unsigned int n_components   = this->dofs->get_fe().n_components();
  const unsigned int n_datasets     = this->dof_data.size() * n_components +
				      this->cell_data.size();

				   // clear the patches array
  if (true)
    {
      std::vector< ::DataOutBase::Patch<dim-1,dim> > dummy;
      this->patches.swap (dummy);
    };

				   // first count the cells we want to
				   // create patches of and make sure
				   // there is enough memory for that
  unsigned int n_patches = 0;
  for (FaceDescriptor face=first_face();
       face.first != this->dofs->end();
       face = next_face(face))
    ++n_patches;

  std::vector<Data> thread_data(n_threads);

				   // init data for the threads
  for (unsigned int i=0;i<n_threads;++i)
    {
      thread_data[i].n_threads            = n_threads;
      thread_data[i].this_thread          = i;
      thread_data[i].n_components         = n_components;
      thread_data[i].n_datasets           = n_datasets;
      thread_data[i].n_subdivisions       = n_subdivisions;
      thread_data[i].patch_values.resize (n_q_points);
      thread_data[i].patch_values_system.resize (n_q_points);

      for (unsigned int k=0; k<n_q_points; ++k)
	thread_data[i].patch_values_system[k].reinit(n_components);
    }

				   // create the patches with default
				   // values. note that the evaluation
				   // points on the face have to be
				   // repeated in angular direction
  ::DataOutBase::Patch<dim-1,dim>  default_patch;
  default_patch.n_subdivisions = n_subdivisions;
  default_patch.data.reinit (n_datasets, n_q_points);
  this->patches.insert (this->patches.end(), n_patches, default_patch);

  if (DEAL_II_USE_MT)
    {
      Threads::ThreadGroup<> threads;
      for (unsigned int l=0;l<n_threads;++l)
        threads += Threads::spawn (*this, &DataOutFaces<dim,DH>::build_some_patches)(thread_data[l]);
      threads.join_all();
    }
  else
				   // just one thread
    build_some_patches(thread_data[0]);
}

template <int dim, template <int> class DH>
typename DataOutFaces<dim,DH>::FaceDescriptor
DataOutFaces<dim,DH>::first_face ()
{
				   // simply find first active cell
				   // with a face on the boundary
  typename DH<dim>::active_cell_iterator cell = this->dofs->begin_active();
  for (; cell != this->dofs->end(); ++cell)
    for (unsigned int f=0; f<GeometryInfo<dim>::faces_per_cell; ++f)
      if (cell->face(f)->at_boundary())
	return FaceDescriptor(cell, f);

				   // ups, triangulation has no
				   // boundary? impossible!
  Assert (false, ExcInternalError());

  return FaceDescriptor();
}

template <int dim, template <int> class DH>
typename DataOutFaces<dim,DH>::FaceDescriptor
DataOutFaces<dim,DH>::next_face (const FaceDescriptor &old_face)
{
  FaceDescriptor face = old_face;

				   // first check whether the present
				   // cell has more faces on the
				   // boundary
  for (unsigned int f=face.second+1; f<GeometryInfo<dim>::faces_per_cell; ++f)
    if (face.first->face(f)->at_boundary())
				       // yup, that is so, so return it
      {
	face.second = f;
	return face;
      };

				   // otherwise find the next active
				   // cell that has a face on the
				   // boundary

				   // convert the iterator to an
				   // active_iterator and advance
				   // this to the next active cell
  typename DH<dim>::active_cell_iterator active_cell = face.first;

				   // increase face pointer by one
  ++active_cell;

				   // while there are active cells
  while (active_cell != this->dofs->end())
    {
				       // check all the faces of this
				       // active cell
      for (unsigned int f=0; f<GeometryInfo<dim>::faces_per_cell; ++f)
	if (active_cell->face(f)->at_boundary())
	  {
	    face.first  = active_cell;
	    face.second = f;
	    return face;
	  };
				       // the present cell had no
				       // faces on the boundary, so
				       // check next cell
      ++active_cell;
    };

				   // we fell off the edge, so return
				   // with invalid pointer
  face.first  = this->dofs->end();
  face.second = 0;
  return face;
}

// explicit instantiations
// don't instantiate anything for the 1d and 2d cases
#if deal_II_dimension >=2
template class DataOutFaces<deal_II_dimension,DoFHandler>;
template class DataOutFaces<deal_II_dimension,hp::DoFHandler>;
#endif
<commit_msg>Bug fix: change to new numbering scheme.<commit_after>//---------------------------------------------------------------------------
//    $Id$
//    Version: $Name$
//
//    Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006 by the deal.II authors
//
//    This file is subject to QPL and may not be  distributed
//    without copyright and license information. Please refer
//    to the file deal.II/doc/license.html for the  text  and
//    further information on this license.
//
//---------------------------------------------------------------------------

#include <base/quadrature_lib.h>
#include <base/thread_management.h>
#include <lac/vector.h>
#include <lac/block_vector.h>
#include <numerics/data_out_faces.h>
#include <grid/tria.h>
#include <dofs/dof_handler.h>
#include <dofs/dof_accessor.h>
#include <grid/tria_iterator.h>
#include <fe/fe.h>
#include <fe/fe_values.h>
#include <fe/hp_fe_values.h>
#include <fe/select_fe_values.h>
#include <fe/mapping_q1.h>

template <int dim, template <int> class DH>
void DataOutFaces<dim,DH>::build_some_patches (Data data)
{
  QTrapez<1>        q_trapez;
  QIterated<dim-1>  patch_points (q_trapez, data.n_subdivisions);

				   // since most output formats can't
				   // handle cells that are not
				   // transformed using a Q1 mapping,
				   // we don't support anything else
				   // as well
  static const MappingQ1<dim> mapping;
  typename SelectFEValues<DH<dim> >::FEFaceValues
    x_fe_patch_values (mapping, this->dofs->get_fe(),
                       patch_points, update_values);

  const unsigned int n_q_points = patch_points.n_quadrature_points;

  typename std::vector< ::DataOutBase::Patch<dim-1,dim> >::iterator patch = this->patches.begin();
  FaceDescriptor face=first_face();

				   // get first face in this thread
  for (unsigned int i=0; (i<data.this_thread)&&(face.first != this->dofs->end()); ++i)
    {
      ++patch;
      face=next_face(face);
    }

  				   // now loop over all cells and
				   // actually create the patches
  for (; face.first != this->dofs->end();)
    {
      Assert (patch != this->patches.end(), ExcInternalError());

      for (unsigned int vertex=0; vertex<GeometryInfo<dim-1>::vertices_per_cell; ++vertex)
	patch->vertices[vertex] = face.first->face(face.second)->vertex(
	  GeometryInfo<dim-1>::ucd_to_deal[vertex]);

      if (data.n_datasets > 0)
	{
	  x_fe_patch_values.reinit (face.first, face.second);
          const FEFaceValues<dim> &fe_patch_values
            = x_fe_patch_values.get_present_fe_values ();

					   // first fill dof_data
	  for (unsigned int dataset=0; dataset<this->dof_data.size(); ++dataset)
	    {
	      if (data.n_components == 1)
		{
                  this->dof_data[dataset]->get_function_values (fe_patch_values,
                                                                data.patch_values);

		  for (unsigned int q=0; q<n_q_points; ++q)
		    patch->data(dataset,q) = data.patch_values[q];
		}
	      else
						 // system of components
		{
                  this->dof_data[dataset]->get_function_values (fe_patch_values,
                                                                data.patch_values_system);

		  for (unsigned int component=0; component<data.n_components;
		       ++component)
		    for (unsigned int q=0; q<n_q_points; ++q)
		      patch->data(dataset*data.n_components+component,q) =
			data.patch_values_system[q](component);
		};
	    };

					   // then do the cell data
	  for (unsigned int dataset=0; dataset<this->cell_data.size(); ++dataset)
	    {
					       // we need to get at
					       // the number of the
					       // cell to which this
					       // face belongs in
					       // order to access the
					       // cell data. this is
					       // not readily
					       // available, so choose
					       // the following rather
					       // inefficient way:
	      Assert (face.first->active(), ExcCellNotActiveForCellData());
	      const unsigned int cell_number
		= std::distance (this->dofs->begin_active(),
				 typename DH<dim>::active_cell_iterator(face.first));

              const double value
                = this->cell_data[dataset]->get_cell_data_value (cell_number);
              for (unsigned int q=0; q<n_q_points; ++q)
                patch->data(dataset+this->dof_data.size()*data.n_components,q) =
                  value;
	    };
	};
      				       // next cell (patch) in this thread
      for (unsigned int i=0;
	   (i<data.n_threads)&&(face.first != this->dofs->end()); ++i)
	{
	  ++patch;
	  face=next_face(face);
	}
    };
}

template <int dim, template <int> class DH>
void DataOutFaces<dim,DH>::build_patches (const unsigned int n_subdivisions,
					  const unsigned int n_threads_)
{
  Assert (n_subdivisions >= 1,
	  ExcInvalidNumberOfSubdivisions(n_subdivisions));

  typedef DataOut_DoFData<dim,DH,dim+1> BaseClass;
  Assert (this->dofs != 0, typename BaseClass::ExcNoDoFHandlerSelected());

  const unsigned int n_threads = (DEAL_II_USE_MT ? n_threads_ : 1);

				   // before we start the loop:
				   // create a quadrature rule that
				   // actually has the points on this
				   // patch
  QTrapez<1>       q_trapez;
  QIterated<dim-1> patch_points (q_trapez, n_subdivisions);

  const unsigned int n_q_points     = patch_points.n_quadrature_points;
  const unsigned int n_components   = this->dofs->get_fe().n_components();
  const unsigned int n_datasets     = this->dof_data.size() * n_components +
				      this->cell_data.size();

				   // clear the patches array
  if (true)
    {
      std::vector< ::DataOutBase::Patch<dim-1,dim> > dummy;
      this->patches.swap (dummy);
    };

				   // first count the cells we want to
				   // create patches of and make sure
				   // there is enough memory for that
  unsigned int n_patches = 0;
  for (FaceDescriptor face=first_face();
       face.first != this->dofs->end();
       face = next_face(face))
    ++n_patches;

  std::vector<Data> thread_data(n_threads);

				   // init data for the threads
  for (unsigned int i=0;i<n_threads;++i)
    {
      thread_data[i].n_threads            = n_threads;
      thread_data[i].this_thread          = i;
      thread_data[i].n_components         = n_components;
      thread_data[i].n_datasets           = n_datasets;
      thread_data[i].n_subdivisions       = n_subdivisions;
      thread_data[i].patch_values.resize (n_q_points);
      thread_data[i].patch_values_system.resize (n_q_points);

      for (unsigned int k=0; k<n_q_points; ++k)
	thread_data[i].patch_values_system[k].reinit(n_components);
    }

				   // create the patches with default
				   // values. note that the evaluation
				   // points on the face have to be
				   // repeated in angular direction
  ::DataOutBase::Patch<dim-1,dim>  default_patch;
  default_patch.n_subdivisions = n_subdivisions;
  default_patch.data.reinit (n_datasets, n_q_points);
  this->patches.insert (this->patches.end(), n_patches, default_patch);

  if (DEAL_II_USE_MT)
    {
      Threads::ThreadGroup<> threads;
      for (unsigned int l=0;l<n_threads;++l)
        threads += Threads::spawn (*this, &DataOutFaces<dim,DH>::build_some_patches)(thread_data[l]);
      threads.join_all();
    }
  else
				   // just one thread
    build_some_patches(thread_data[0]);
}

template <int dim, template <int> class DH>
typename DataOutFaces<dim,DH>::FaceDescriptor
DataOutFaces<dim,DH>::first_face ()
{
				   // simply find first active cell
				   // with a face on the boundary
  typename DH<dim>::active_cell_iterator cell = this->dofs->begin_active();
  for (; cell != this->dofs->end(); ++cell)
    for (unsigned int f=0; f<GeometryInfo<dim>::faces_per_cell; ++f)
      if (cell->face(f)->at_boundary())
	return FaceDescriptor(cell, f);

				   // ups, triangulation has no
				   // boundary? impossible!
  Assert (false, ExcInternalError());

  return FaceDescriptor();
}

template <int dim, template <int> class DH>
typename DataOutFaces<dim,DH>::FaceDescriptor
DataOutFaces<dim,DH>::next_face (const FaceDescriptor &old_face)
{
  FaceDescriptor face = old_face;

				   // first check whether the present
				   // cell has more faces on the
				   // boundary
  for (unsigned int f=face.second+1; f<GeometryInfo<dim>::faces_per_cell; ++f)
    if (face.first->face(f)->at_boundary())
				       // yup, that is so, so return it
      {
	face.second = f;
	return face;
      };

				   // otherwise find the next active
				   // cell that has a face on the
				   // boundary

				   // convert the iterator to an
				   // active_iterator and advance
				   // this to the next active cell
  typename DH<dim>::active_cell_iterator active_cell = face.first;

				   // increase face pointer by one
  ++active_cell;

				   // while there are active cells
  while (active_cell != this->dofs->end())
    {
				       // check all the faces of this
				       // active cell
      for (unsigned int f=0; f<GeometryInfo<dim>::faces_per_cell; ++f)
	if (active_cell->face(f)->at_boundary())
	  {
	    face.first  = active_cell;
	    face.second = f;
	    return face;
	  };
				       // the present cell had no
				       // faces on the boundary, so
				       // check next cell
      ++active_cell;
    };

				   // we fell off the edge, so return
				   // with invalid pointer
  face.first  = this->dofs->end();
  face.second = 0;
  return face;
}

// explicit instantiations
// don't instantiate anything for the 1d and 2d cases
#if deal_II_dimension >=2
template class DataOutFaces<deal_II_dimension,DoFHandler>;
template class DataOutFaces<deal_II_dimension,hp::DoFHandler>;
#endif
<|endoftext|>


<commit_before>//---------------------------------------------------------------------------
//    $Id$
//    Version: $Name$
//
//    Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2008 by the deal.II authors
//
//    This file is subject to QPL and may not be  distributed
//    without copyright and license information. Please refer
//    to the file deal.II/doc/license.html for the  text  and
//    further information on this license.
//
//---------------------------------------------------------------------------

#include <lac/compressed_sparsity_pattern.h>

#include <iostream>
#include <iomanip>
#include <algorithm>
#include <cmath>
#include <numeric>
#include <functional>

DEAL_II_NAMESPACE_OPEN

const unsigned int CompressedSparsityPattern::Line::cache_size;

// This function was originally inlined, because it was called very
// often without any need, because cache_entries==0. On the other
// hand, it is very long and causes linker warnings on certain
// systems.

// Therefore, we require now, that the caller checks if this function
// is necessary and only calls it, if it is actually used. Since it is
// it called less often, it is removed from the inlined section.
void
CompressedSparsityPattern::Line::flush_cache () const
{
                                   // Make sure the caller checked
                                   // necessity of this function.
  Assert(cache_entries != 0, ExcInternalError());

                                   // first sort the entries in the cache, so
                                   // that it is easier to merge it with the
                                   // main array. note that due to the way
                                   // add() inserts elements, there can be no
                                   // duplicates in the cache
                                   //
                                   // do the sorting in a way that is fast for
                                   // the small cache sizes we have
                                   // here. basically, use bubble sort
  switch (cache_entries)
    {
      case 1:
      {
        break;
      }

      case 2:
      {
        if (cache[1] < cache[0])
          std::swap (cache[0], cache[1]);
        break;
      }

      case 3:
      {
        if (cache[1] < cache[0])
          std::swap (cache[0], cache[1]);
        if (cache[2] < cache[1])
          std::swap (cache[1], cache[2]);
        if (cache[1] < cache[0])
          std::swap (cache[0], cache[1]);
        break;
      }

      case 4:
      case 5:
      case 6:
      case 7:
      {
        for (unsigned int i=0; i<cache_entries; ++i)
          for (unsigned int j=i+1; j<cache_entries; ++j)
            if (cache[j] < cache[i])
              std::swap (cache[i], cache[j]);
        break;
      }

      default:
      {
        std::sort (&cache[0], &cache[cache_entries]);
        break;
      }
    }

                                   // next job is to merge the two
                                   // arrays. special case the case that the
                                   // original array is empty.
  if (entries.size() == 0)
    {
      entries.resize (cache_entries);
      for (unsigned int i=0; i<cache_entries; ++i)
        entries[i] = cache[i];
    }
  else
    {
                                       // first count how many of the cache
                                       // entries are already in the main
                                       // array, so that we can efficiently
                                       // allocate memory
      unsigned int n_new_entries = 0;
      {
        unsigned int cache_position = 0;
        unsigned int entry_position = 0;
        while ((entry_position<entries.size()) &&
               (cache_position<cache_entries))
          {
            ++n_new_entries;
            if (entries[entry_position] < cache[cache_position])
              ++entry_position;
            else if (entries[entry_position] == cache[cache_position])
              {
                ++entry_position;
                ++cache_position;
              }
            else
              ++cache_position;
          }

                                         // scoop up leftovers in arrays
        n_new_entries += (entries.size() - entry_position) +
                         (cache_entries - cache_position);
      }

                                       // then allocate new memory and merge
                                       // arrays
      std::vector<unsigned int> new_entries;
      new_entries.reserve (n_new_entries);
      unsigned int cache_position = 0;
      unsigned int entry_position = 0;
      while ((entry_position<entries.size()) && (cache_position<cache_entries))
        if (entries[entry_position] < cache[cache_position])
          {
            new_entries.push_back (entries[entry_position]);
            ++entry_position;
          }
        else if (entries[entry_position] == cache[cache_position])
          {
            new_entries.push_back (entries[entry_position]);
            ++entry_position;
            ++cache_position;
          }
        else
          {
            new_entries.push_back (cache[cache_position]);
            ++cache_position;
          }

                                       // copy remaining elements from the
                                       // array that we haven't finished. note
                                       // that at most one of the following
                                       // loops will run at all
      for (; entry_position < entries.size(); ++entry_position)
        new_entries.push_back (entries[entry_position]);
      for (; cache_position < cache_entries; ++cache_position)
        new_entries.push_back (cache[cache_position]);

      Assert (new_entries.size() == n_new_entries,
              ExcInternalError());

                                       // finally swap old and new array, and
                                       // set cache size to zero
      new_entries.swap (entries);
    }

  cache_entries = 0;
}

CompressedSparsityPattern::CompressedSparsityPattern ()
                :
		rows(0),
		cols(0)
{}

CompressedSparsityPattern::
CompressedSparsityPattern (const CompressedSparsityPattern &s)
                :
		Subscriptor(),
		rows(0),
		cols(0)
{
  Assert (s.rows == 0, ExcInvalidConstructorCall());
  Assert (s.cols == 0, ExcInvalidConstructorCall());
}

CompressedSparsityPattern::CompressedSparsityPattern (const unsigned int m,
						      const unsigned int n)
		:
                rows(0),
                cols(0)
{
  reinit (m,n);
}

CompressedSparsityPattern::CompressedSparsityPattern (const unsigned int n)
		:
                rows(0),
                cols(0)
{
  reinit (n,n);
}

CompressedSparsityPattern &
CompressedSparsityPattern::operator = (const CompressedSparsityPattern &s)
{
  Assert (s.rows == 0, ExcInvalidConstructorCall());
  Assert (s.cols == 0, ExcInvalidConstructorCall());

  Assert (rows == 0, ExcInvalidConstructorCall());
  Assert (cols == 0, ExcInvalidConstructorCall());

  return *this;
}

void
CompressedSparsityPattern::reinit (const unsigned int m,
				   const unsigned int n)
{
  rows = m;
  cols = n;

  std::vector<Line> new_lines (rows);
  lines.swap (new_lines);
}

void
CompressedSparsityPattern::compress ()
{}

bool
CompressedSparsityPattern::empty () const
{
  return ((rows==0) && (cols==0));
}

unsigned int
CompressedSparsityPattern::max_entries_per_row () const
{
  unsigned int m = 0;
  for (unsigned int i=0; i<rows; ++i)
    {
      if (lines[i].cache_entries != 0)
	lines[i].flush_cache ();
      m = std::max (m, static_cast<unsigned int>(lines[i].entries.size()));
    }

  return m;
}

bool
CompressedSparsityPattern::exists (const unsigned int i,
				   const unsigned int j) const
{
  Assert (i<rows, ExcIndexRange(i, 0, rows));
  Assert (j<cols, ExcIndexRange(j, 0, cols));

  if (lines[i].cache_entries != 0)
    lines[i].flush_cache();
  return std::binary_search (lines[i].entries.begin(),
                             lines[i].entries.end(),
                             j);
}

void
CompressedSparsityPattern::symmetrize ()
{
  Assert (rows==cols, ExcNotQuadratic());

				   // loop over all elements presently
				   // in the sparsity pattern and add
				   // the transpose element. note:
				   //
				   // 1. that the sparsity pattern
				   // changes which we work on, but
				   // not the present row
				   //
				   // 2. that the @p{add} function can
				   // be called on elements that
				   // already exist without any harm
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();
      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end();
           ++j)
				       // add the transpose entry if
				       // this is not the diagonal
        if (row != *j)
          add (*j, row);
    }
}

void
CompressedSparsityPattern::print (std::ostream &out) const
{
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();

      out << row << ' ';

      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end(); ++j)
        out << *j << ' ';

      out << std::endl;
    }

  AssertThrow (out, ExcIO());
}

void
CompressedSparsityPattern::print_gnuplot (std::ostream &out) const
{
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();
      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end(); ++j)
                                         // while matrix entries are usually
                                         // written (i,j), with i vertical and
                                         // j horizontal, gnuplot output is
                                         // x-y, that is we have to exchange
                                         // the order of output
        out << *j << " " << -static_cast<signed int>(row) << std::endl;
    }

  AssertThrow (out, ExcIO());
}

unsigned int
CompressedSparsityPattern::bandwidth () const
{
  unsigned int b=0;
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();

      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end(); ++j)
        if (static_cast<unsigned int>(std::abs(static_cast<int>(row-*j))) > b)
          b = std::abs(static_cast<signed int>(row-*j));
    }

  return b;
}

unsigned int
CompressedSparsityPattern::n_nonzero_elements () const
{
  unsigned int n=0;
  for (unsigned int i=0; i<rows; ++i)
    {
      if (lines[i].cache_entries != 0)
	lines[i].flush_cache ();
      n += lines[i].entries.size();
    }

  return n;
}

DEAL_II_NAMESPACE_CLOSE
<commit_msg>Fix format in CompressedSparsityPattern::print.<commit_after>//---------------------------------------------------------------------------
//    $Id$
//    Version: $Name$
//
//    Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2008 by the deal.II authors
//
//    This file is subject to QPL and may not be  distributed
//    without copyright and license information. Please refer
//    to the file deal.II/doc/license.html for the  text  and
//    further information on this license.
//
//---------------------------------------------------------------------------

#include <lac/compressed_sparsity_pattern.h>

#include <iostream>
#include <iomanip>
#include <algorithm>
#include <cmath>
#include <numeric>
#include <functional>

DEAL_II_NAMESPACE_OPEN

const unsigned int CompressedSparsityPattern::Line::cache_size;

// This function was originally inlined, because it was called very
// often without any need, because cache_entries==0. On the other
// hand, it is very long and causes linker warnings on certain
// systems.

// Therefore, we require now, that the caller checks if this function
// is necessary and only calls it, if it is actually used. Since it is
// it called less often, it is removed from the inlined section.
void
CompressedSparsityPattern::Line::flush_cache () const
{
                                   // Make sure the caller checked
                                   // necessity of this function.
  Assert(cache_entries != 0, ExcInternalError());

                                   // first sort the entries in the cache, so
                                   // that it is easier to merge it with the
                                   // main array. note that due to the way
                                   // add() inserts elements, there can be no
                                   // duplicates in the cache
                                   //
                                   // do the sorting in a way that is fast for
                                   // the small cache sizes we have
                                   // here. basically, use bubble sort
  switch (cache_entries)
    {
      case 1:
      {
        break;
      }

      case 2:
      {
        if (cache[1] < cache[0])
          std::swap (cache[0], cache[1]);
        break;
      }

      case 3:
      {
        if (cache[1] < cache[0])
          std::swap (cache[0], cache[1]);
        if (cache[2] < cache[1])
          std::swap (cache[1], cache[2]);
        if (cache[1] < cache[0])
          std::swap (cache[0], cache[1]);
        break;
      }

      case 4:
      case 5:
      case 6:
      case 7:
      {
        for (unsigned int i=0; i<cache_entries; ++i)
          for (unsigned int j=i+1; j<cache_entries; ++j)
            if (cache[j] < cache[i])
              std::swap (cache[i], cache[j]);
        break;
      }

      default:
      {
        std::sort (&cache[0], &cache[cache_entries]);
        break;
      }
    }

                                   // next job is to merge the two
                                   // arrays. special case the case that the
                                   // original array is empty.
  if (entries.size() == 0)
    {
      entries.resize (cache_entries);
      for (unsigned int i=0; i<cache_entries; ++i)
        entries[i] = cache[i];
    }
  else
    {
                                       // first count how many of the cache
                                       // entries are already in the main
                                       // array, so that we can efficiently
                                       // allocate memory
      unsigned int n_new_entries = 0;
      {
        unsigned int cache_position = 0;
        unsigned int entry_position = 0;
        while ((entry_position<entries.size()) &&
               (cache_position<cache_entries))
          {
            ++n_new_entries;
            if (entries[entry_position] < cache[cache_position])
              ++entry_position;
            else if (entries[entry_position] == cache[cache_position])
              {
                ++entry_position;
                ++cache_position;
              }
            else
              ++cache_position;
          }

                                         // scoop up leftovers in arrays
        n_new_entries += (entries.size() - entry_position) +
                         (cache_entries - cache_position);
      }

                                       // then allocate new memory and merge
                                       // arrays
      std::vector<unsigned int> new_entries;
      new_entries.reserve (n_new_entries);
      unsigned int cache_position = 0;
      unsigned int entry_position = 0;
      while ((entry_position<entries.size()) && (cache_position<cache_entries))
        if (entries[entry_position] < cache[cache_position])
          {
            new_entries.push_back (entries[entry_position]);
            ++entry_position;
          }
        else if (entries[entry_position] == cache[cache_position])
          {
            new_entries.push_back (entries[entry_position]);
            ++entry_position;
            ++cache_position;
          }
        else
          {
            new_entries.push_back (cache[cache_position]);
            ++cache_position;
          }

                                       // copy remaining elements from the
                                       // array that we haven't finished. note
                                       // that at most one of the following
                                       // loops will run at all
      for (; entry_position < entries.size(); ++entry_position)
        new_entries.push_back (entries[entry_position]);
      for (; cache_position < cache_entries; ++cache_position)
        new_entries.push_back (cache[cache_position]);

      Assert (new_entries.size() == n_new_entries,
              ExcInternalError());

                                       // finally swap old and new array, and
                                       // set cache size to zero
      new_entries.swap (entries);
    }

  cache_entries = 0;
}

CompressedSparsityPattern::CompressedSparsityPattern ()
                :
		rows(0),
		cols(0)
{}

CompressedSparsityPattern::
CompressedSparsityPattern (const CompressedSparsityPattern &s)
                :
		Subscriptor(),
		rows(0),
		cols(0)
{
  Assert (s.rows == 0, ExcInvalidConstructorCall());
  Assert (s.cols == 0, ExcInvalidConstructorCall());
}

CompressedSparsityPattern::CompressedSparsityPattern (const unsigned int m,
						      const unsigned int n)
		:
                rows(0),
                cols(0)
{
  reinit (m,n);
}

CompressedSparsityPattern::CompressedSparsityPattern (const unsigned int n)
		:
                rows(0),
                cols(0)
{
  reinit (n,n);
}

CompressedSparsityPattern &
CompressedSparsityPattern::operator = (const CompressedSparsityPattern &s)
{
  Assert (s.rows == 0, ExcInvalidConstructorCall());
  Assert (s.cols == 0, ExcInvalidConstructorCall());

  Assert (rows == 0, ExcInvalidConstructorCall());
  Assert (cols == 0, ExcInvalidConstructorCall());

  return *this;
}

void
CompressedSparsityPattern::reinit (const unsigned int m,
				   const unsigned int n)
{
  rows = m;
  cols = n;

  std::vector<Line> new_lines (rows);
  lines.swap (new_lines);
}

void
CompressedSparsityPattern::compress ()
{}

bool
CompressedSparsityPattern::empty () const
{
  return ((rows==0) && (cols==0));
}

unsigned int
CompressedSparsityPattern::max_entries_per_row () const
{
  unsigned int m = 0;
  for (unsigned int i=0; i<rows; ++i)
    {
      if (lines[i].cache_entries != 0)
	lines[i].flush_cache ();
      m = std::max (m, static_cast<unsigned int>(lines[i].entries.size()));
    }

  return m;
}

bool
CompressedSparsityPattern::exists (const unsigned int i,
				   const unsigned int j) const
{
  Assert (i<rows, ExcIndexRange(i, 0, rows));
  Assert (j<cols, ExcIndexRange(j, 0, cols));

  if (lines[i].cache_entries != 0)
    lines[i].flush_cache();
  return std::binary_search (lines[i].entries.begin(),
                             lines[i].entries.end(),
                             j);
}

void
CompressedSparsityPattern::symmetrize ()
{
  Assert (rows==cols, ExcNotQuadratic());

				   // loop over all elements presently
				   // in the sparsity pattern and add
				   // the transpose element. note:
				   //
				   // 1. that the sparsity pattern
				   // changes which we work on, but
				   // not the present row
				   //
				   // 2. that the @p{add} function can
				   // be called on elements that
				   // already exist without any harm
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();
      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end();
           ++j)
				       // add the transpose entry if
				       // this is not the diagonal
        if (row != *j)
          add (*j, row);
    }
}

void
CompressedSparsityPattern::print (std::ostream &out) const
{
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();

      out << '[' << row << ' ';

      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end(); ++j)
        out << *j << ' ';

      out << ']' << std::endl;
    }

  AssertThrow (out, ExcIO());
}

void
CompressedSparsityPattern::print_gnuplot (std::ostream &out) const
{
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();
      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end(); ++j)
                                         // while matrix entries are usually
                                         // written (i,j), with i vertical and
                                         // j horizontal, gnuplot output is
                                         // x-y, that is we have to exchange
                                         // the order of output
        out << *j << " " << -static_cast<signed int>(row) << std::endl;
    }

  AssertThrow (out, ExcIO());
}

unsigned int
CompressedSparsityPattern::bandwidth () const
{
  unsigned int b=0;
  for (unsigned int row=0; row<rows; ++row)
    {
      if (lines[row].cache_entries != 0)
	lines[row].flush_cache ();

      for (std::vector<unsigned int>::const_iterator
             j=lines[row].entries.begin();
           j != lines[row].entries.end(); ++j)
        if (static_cast<unsigned int>(std::abs(static_cast<int>(row-*j))) > b)
          b = std::abs(static_cast<signed int>(row-*j));
    }

  return b;
}

unsigned int
CompressedSparsityPattern::n_nonzero_elements () const
{
  unsigned int n=0;
  for (unsigned int i=0; i<rows; ++i)
    {
      if (lines[i].cache_entries != 0)
	lines[i].flush_cache ();
      n += lines[i].entries.size();
    }

  return n;
}

DEAL_II_NAMESPACE_CLOSE
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: dp_backend.cxx,v $
 *
 *  $Revision: 1.9 $
 *
 *  last change: $Author: rt $ $Date: 2006-03-06 10:21:41 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

#include "dp_backend.h"
#include "dp_ucb.h"
#include "rtl/uri.hxx"
#include "cppuhelper/exc_hlp.hxx"
#include "comphelper/servicedecl.hxx"
#include "comphelper/unwrapargs.hxx"
#include "ucbhelper/content.hxx"
#include "com/sun/star/lang/WrappedTargetRuntimeException.hpp"

using namespace ::dp_misc;
using namespace ::com::sun::star;
using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::ucb;
using ::rtl::OUString;

namespace dp_registry {
namespace backend {

//______________________________________________________________________________
PackageRegistryBackend::~PackageRegistryBackend()
{
}

//______________________________________________________________________________
void PackageRegistryBackend::disposing( lang::EventObject const & event )
    throw (RuntimeException)
{
    Reference<deployment::XPackage> xPackage(
        event.Source, UNO_QUERY_THROW );
    OUString url( xPackage->getURL() );
    ::osl::MutexGuard guard( getMutex() );
    ::std::size_t erased = m_bound.erase( url );
    OSL_ASSERT( erased == 1 );
}

//______________________________________________________________________________
PackageRegistryBackend::PackageRegistryBackend(
    Sequence<Any> const & args,
    Reference<XComponentContext> const & xContext )
    : t_BackendBase( getMutex() ),
      m_xComponentContext( xContext ),
      m_eContext( CONTEXT_UNKNOWN ),
      m_readOnly( false )
{
    boost::optional<OUString> cachePath;
    boost::optional<bool> readOnly;
    comphelper::unwrapArgs( args, m_context, cachePath, readOnly );
    if (cachePath)
        m_cachePath = *cachePath;
    if (readOnly)
        m_readOnly = *readOnly;

    if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("user") ))
        m_eContext = CONTEXT_USER;
    else if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("shared") ))
        m_eContext = CONTEXT_SHARED;
    else if (m_context.matchIgnoreAsciiCaseAsciiL(
                 RTL_CONSTASCII_STRINGPARAM("vnd.sun.star.tdoc:/") ))
        m_eContext = CONTEXT_DOCUMENT;
    else
        m_eContext = CONTEXT_UNKNOWN;
}

//______________________________________________________________________________
void PackageRegistryBackend::check()
{
    ::osl::MutexGuard guard( getMutex() );
    if (rBHelper.bInDispose || rBHelper.bDisposed) {
        throw lang::DisposedException(
            OUSTR("PackageRegistryBackend instance has already been disposed!"),
            static_cast<OWeakObject *>(this) );
    }
}

//______________________________________________________________________________
void PackageRegistryBackend::disposing()
{
    try {
        m_xComponentContext.clear();
        WeakComponentImplHelperBase::disposing();
    }
    catch (RuntimeException &) {
        throw;
    }
    catch (Exception &) {
        Any exc( ::cppu::getCaughtException() );
        throw lang::WrappedTargetRuntimeException(
            OUSTR("caught unexpected exception while disposing!"),
            static_cast<OWeakObject *>(this), exc );
    }
}

// XPackageRegistry
//______________________________________________________________________________
Reference<deployment::XPackage> PackageRegistryBackend::bindPackage(
    OUString const & url, OUString const & mediaType,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException, CommandFailedException,
           lang::IllegalArgumentException, RuntimeException)
{
    ::osl::ResettableMutexGuard guard( getMutex() );
    check();
    t_string2weakref::const_iterator const iFind( m_bound.find( url ) );
    if (iFind != m_bound.end()) {
        Reference<deployment::XPackage> xPackage( iFind->second );
        if (xPackage.is())
            return xPackage;
    }
    guard.clear();

    Reference<deployment::XPackage> xNewPackage;
    try {
        xNewPackage = bindPackage_( url, mediaType, xCmdEnv );
    }
    catch (RuntimeException &) {
        throw;
    }
    catch (lang::IllegalArgumentException &) {
        throw;
    }
    catch (CommandFailedException &) {
        throw;
    }
    catch (deployment::DeploymentException &) {
        throw;
    }
    catch (Exception &) {
        Any exc( ::cppu::getCaughtException() );
        throw deployment::DeploymentException(
            OUSTR("Error binding package: ") + url,
            static_cast<OWeakObject *>(this), exc );
    }

    guard.reset();
    ::std::pair< t_string2weakref::iterator, bool > insertion(
        m_bound.insert( t_string2weakref::value_type( url, xNewPackage ) ) );
    if (insertion.second)
    { // first insertion
        OSL_ASSERT( Reference<XInterface>(insertion.first->second)
                    == xNewPackage );
    }
    else
    { // found existing entry
        Reference<deployment::XPackage> xPackage( insertion.first->second );
        if (xPackage.is())
            return xPackage;
        insertion.first->second = xNewPackage;
    }
    guard.clear();
    xNewPackage->addEventListener( this ); // listen for disposing events
    return xNewPackage;
}

//##############################################################################

//______________________________________________________________________________
Package::~Package()
{
}

//______________________________________________________________________________
Package::Package( ::rtl::Reference<PackageRegistryBackend> const & myBackend,
                  OUString const & url,
                  OUString const & name,
                  OUString const & displayName,
                  Reference<deployment::XPackageTypeInfo> const & xPackageType )
    : t_PackageBase( getMutex() ),
      m_myBackend( myBackend ),
      m_url( url ),
      m_name( name ),
      m_displayName( displayName ),
      m_xPackageType( xPackageType )
{
}

//______________________________________________________________________________
void Package::disposing()
{
    m_myBackend.clear();
    WeakComponentImplHelperBase::disposing();
}

//______________________________________________________________________________
void Package::check()
{
    ::osl::MutexGuard guard( getMutex() );
    if (rBHelper.bInDispose || rBHelper.bDisposed) {
        throw lang::DisposedException(
            OUSTR("Package instance has already been disposed!"),
            static_cast<OWeakObject *>(this) );
    }
}

// XComponent
//______________________________________________________________________________
void Package::dispose() throw (RuntimeException)
{
    check();
    WeakComponentImplHelperBase::dispose();
}

//______________________________________________________________________________
void Package::addEventListener(
    Reference<lang::XEventListener> const & xListener ) throw (RuntimeException)
{
    check();
    WeakComponentImplHelperBase::addEventListener( xListener );
}

//______________________________________________________________________________
void Package::removeEventListener(
    Reference<lang::XEventListener> const & xListener ) throw (RuntimeException)
{
    check();
    WeakComponentImplHelperBase::removeEventListener( xListener );
}

// XModifyBroadcaster
//______________________________________________________________________________
void Package::addModifyListener(
    Reference<util::XModifyListener> const & xListener )
    throw (RuntimeException)
{
    check();
    rBHelper.addListener( ::getCppuType( &xListener ), xListener );
}

//______________________________________________________________________________
void Package::removeModifyListener(
    Reference<util::XModifyListener> const & xListener )
    throw (RuntimeException)
{
    check();
    rBHelper.removeListener( ::getCppuType( &xListener ), xListener );
}

//______________________________________________________________________________
void Package::checkAborted(
    ::rtl::Reference<AbortChannel> const & abortChannel )
{
    if (abortChannel.is() && abortChannel->isAborted()) {
        throw CommandAbortedException(
            OUSTR("abort!"), static_cast<OWeakObject *>(this) );
    }
}

// XPackage
//______________________________________________________________________________
Reference<task::XAbortChannel> Package::createAbortChannel()
    throw (RuntimeException)
{
    check();
    return new AbortChannel;
}

//______________________________________________________________________________
sal_Bool Package::isBundle() throw (RuntimeException)
{
    return false; // default
}

//______________________________________________________________________________
Sequence< Reference<deployment::XPackage> > Package::getBundle(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException,
           lang::IllegalArgumentException, RuntimeException)
{
    return Sequence< Reference<deployment::XPackage> >();
}

//______________________________________________________________________________
OUString Package::getName() throw (RuntimeException)
{
    return m_name;
}

//______________________________________________________________________________
OUString Package::getURL() throw (RuntimeException)
{
    return m_url;
}

//______________________________________________________________________________
OUString Package::getDisplayName() throw (RuntimeException)
{
    return m_displayName;
}

//______________________________________________________________________________
OUString Package::getDescription() throw (RuntimeException)
{
    if (m_xPackageType.is())
        return m_xPackageType->getDescription();
    else
        return OUString();
}

//______________________________________________________________________________
Reference<deployment::XPackageTypeInfo> Package::getPackageType()
    throw (RuntimeException)
{
    return m_xPackageType;
}

//______________________________________________________________________________
void Package::exportTo(
    OUString const & destFolderURL, OUString const & newTitle,
    sal_Int32 nameClashAction, Reference<XCommandEnvironment> const & xCmdEnv )
    throw (CommandFailedException, CommandAbortedException, RuntimeException)
{
    ::ucb::Content destFolder( destFolderURL, xCmdEnv );
    ::ucb::Content sourceContent( getURL(), xCmdEnv );
    if (! destFolder.transferContent(
            sourceContent, ::ucb::InsertOperation_COPY,
            newTitle, nameClashAction ))
        throw RuntimeException( OUSTR("UCB transferContent() failed!"), 0 );
}

//______________________________________________________________________________
void Package::fireModified()
{
    ::cppu::OInterfaceContainerHelper * container = rBHelper.getContainer(
        ::getCppuType( static_cast<Reference<
                       util::XModifyListener> const *>(0) ) );
    if (container != 0) {
        Sequence< Reference<XInterface> > elements(
            container->getElements() );
        lang::EventObject evt( static_cast<OWeakObject *>(this) );
        for ( sal_Int32 pos = 0; pos < elements.getLength(); ++pos )
        {
            Reference<util::XModifyListener> xListener(
                elements[ pos ], UNO_QUERY );
            if (xListener.is())
                xListener->modified( evt );
        }
    }
}

// XPackage
//______________________________________________________________________________
beans::Optional< beans::Ambiguous<sal_Bool> > Package::isRegistered(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException, RuntimeException)
{
    try {
        ::osl::ResettableMutexGuard guard( getMutex() );
        return isRegistered_( guard,
                              AbortChannel::get(xAbortChannel),
                              xCmdEnv );
    }
    catch (RuntimeException &) {
        throw;
    }
    catch (CommandFailedException &) {
        throw;
    }
    catch (CommandAbortedException &) {
        throw;
    }
    catch (deployment::DeploymentException &) {
        throw;
    }
    catch (Exception &) {
        Any exc( ::cppu::getCaughtException() );
        throw deployment::DeploymentException(
            OUSTR("unexpected exception occured!"),
            static_cast<OWeakObject *>(this), exc );
    }
}

//______________________________________________________________________________
void Package::processPackage_(
    bool registerPackage,
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
{
    check();
    bool action = false;

    try {
        try {
            ::osl::ResettableMutexGuard guard( getMutex() );
            beans::Optional< beans::Ambiguous<sal_Bool> > option(
                isRegistered_( guard, AbortChannel::get(xAbortChannel),
                               xCmdEnv ) );
            action = (option.IsPresent &&
                      (option.Value.IsAmbiguous ||
                       (registerPackage ? !option.Value.Value
                                        : option.Value.Value)));
            if (action) {
                OUString displayName( getDisplayName() );
                ProgressLevel progress(
                    xCmdEnv,
                    (registerPackage
                     ? PackageRegistryBackend::StrRegisteringPackage::get()
                     : PackageRegistryBackend::StrRevokingPackage::get())
                    + displayName );
                processPackage_( guard,
                                 registerPackage,
                                 AbortChannel::get(xAbortChannel),
                                 xCmdEnv );
            }
        }
        catch (RuntimeException &) {
            OSL_ENSURE( 0, "### unexpected RuntimeException!" );
            throw;
        }
        catch (CommandFailedException &) {
            throw;
        }
        catch (CommandAbortedException &) {
            throw;
        }
        catch (deployment::DeploymentException &) {
            throw;
        }
        catch (Exception &) {
            Any exc( ::cppu::getCaughtException() );
            throw deployment::DeploymentException(
                (registerPackage
                 ? getResourceString(RID_STR_ERROR_WHILE_REGISTERING)
                 : getResourceString(RID_STR_ERROR_WHILE_REVOKING))
                + getDisplayName(), static_cast<OWeakObject *>(this), exc );
        }
    }
    catch (...) {
        if (action)
            fireModified();
        throw;
    }
    if (action)
        fireModified();
}

//______________________________________________________________________________
void Package::registerPackage(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException,
           lang::IllegalArgumentException, RuntimeException)
{
    processPackage_( true /* register */, xAbortChannel, xCmdEnv );
}

//______________________________________________________________________________
void Package::revokePackage(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException,
           lang::IllegalArgumentException, RuntimeException)
{
    processPackage_( false /* revoke */, xAbortChannel, xCmdEnv );
}

//##############################################################################

//______________________________________________________________________________
Package::TypeInfo::~TypeInfo()
{
}

// XPackageTypeInfo
//______________________________________________________________________________
OUString Package::TypeInfo::getMediaType() throw (RuntimeException)
{
    return m_mediaType;
}

//______________________________________________________________________________
OUString Package::TypeInfo::getDescription() throw (RuntimeException)
{
    return getShortDescription();
}

//______________________________________________________________________________
OUString Package::TypeInfo::getShortDescription() throw (RuntimeException)
{
    return m_shortDescr;
}

//______________________________________________________________________________
OUString Package::TypeInfo::getFileFilter() throw (RuntimeException)
{
    return m_fileFilter;
}

//______________________________________________________________________________
Any Package::TypeInfo::getIcon( sal_Bool highContrast, sal_Bool smallIcon )
    throw (RuntimeException)
{
    if (! smallIcon)
        return Any();
    const sal_uInt16 nIconId = (highContrast ? m_smallIcon_HC : m_smallIcon);
    return Any( &nIconId, getCppuType( static_cast<sal_uInt16 const *>(0) ) );
}

}
}

<commit_msg>INTEGRATION: CWS jsc7 (1.9.12); FILE MERGED 2006/06/28 07:21:53 jl 1.9.12.1: #66211# support of license files in extensions<commit_after>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: dp_backend.cxx,v $
 *
 *  $Revision: 1.10 $
 *
 *  last change: $Author: obo $ $Date: 2006-07-13 17:06:05 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

#include "dp_backend.h"
#include "dp_ucb.h"
#include "rtl/uri.hxx"
#include "cppuhelper/exc_hlp.hxx"
#include "comphelper/servicedecl.hxx"
#include "comphelper/unwrapargs.hxx"
#include "ucbhelper/content.hxx"
#include "com/sun/star/lang/WrappedTargetRuntimeException.hpp"

using namespace ::dp_misc;
using namespace ::com::sun::star;
using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::ucb;
using ::rtl::OUString;

namespace dp_registry {
namespace backend {

//______________________________________________________________________________
PackageRegistryBackend::~PackageRegistryBackend()
{
}

//______________________________________________________________________________
void PackageRegistryBackend::disposing( lang::EventObject const & event )
    throw (RuntimeException)
{
    Reference<deployment::XPackage> xPackage(
        event.Source, UNO_QUERY_THROW );
    OUString url( xPackage->getURL() );
    ::osl::MutexGuard guard( getMutex() );
    ::std::size_t erased = m_bound.erase( url );
    OSL_ASSERT( erased == 1 );
}

//______________________________________________________________________________
PackageRegistryBackend::PackageRegistryBackend(
    Sequence<Any> const & args,
    Reference<XComponentContext> const & xContext )
    : t_BackendBase( getMutex() ),
      m_xComponentContext( xContext ),
      m_eContext( CONTEXT_UNKNOWN ),
      m_readOnly( false )
{
    boost::optional<OUString> cachePath;
    boost::optional<bool> readOnly;
    comphelper::unwrapArgs( args, m_context, cachePath, readOnly );
    if (cachePath)
        m_cachePath = *cachePath;
    if (readOnly)
        m_readOnly = *readOnly;

    if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("user") ))
        m_eContext = CONTEXT_USER;
    else if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("shared") ))
        m_eContext = CONTEXT_SHARED;
    else if (m_context.matchIgnoreAsciiCaseAsciiL(
                 RTL_CONSTASCII_STRINGPARAM("vnd.sun.star.tdoc:/") ))
        m_eContext = CONTEXT_DOCUMENT;
    else
        m_eContext = CONTEXT_UNKNOWN;
}

//______________________________________________________________________________
void PackageRegistryBackend::check()
{
    ::osl::MutexGuard guard( getMutex() );
    if (rBHelper.bInDispose || rBHelper.bDisposed) {
        throw lang::DisposedException(
            OUSTR("PackageRegistryBackend instance has already been disposed!"),
            static_cast<OWeakObject *>(this) );
    }
}

//______________________________________________________________________________
void PackageRegistryBackend::disposing()
{
    try {
        m_xComponentContext.clear();
        WeakComponentImplHelperBase::disposing();
    }
    catch (RuntimeException &) {
        throw;
    }
    catch (Exception &) {
        Any exc( ::cppu::getCaughtException() );
        throw lang::WrappedTargetRuntimeException(
            OUSTR("caught unexpected exception while disposing!"),
            static_cast<OWeakObject *>(this), exc );
    }
}

// XPackageRegistry
//______________________________________________________________________________
Reference<deployment::XPackage> PackageRegistryBackend::bindPackage(
    OUString const & url, OUString const & mediaType,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException, CommandFailedException,
           lang::IllegalArgumentException, RuntimeException)
{
    ::osl::ResettableMutexGuard guard( getMutex() );
    check();
    t_string2weakref::const_iterator const iFind( m_bound.find( url ) );
    if (iFind != m_bound.end()) {
        Reference<deployment::XPackage> xPackage( iFind->second );
        if (xPackage.is())
            return xPackage;
    }
    guard.clear();

    Reference<deployment::XPackage> xNewPackage;
    try {
        xNewPackage = bindPackage_( url, mediaType, xCmdEnv );
    }
    catch (RuntimeException &) {
        throw;
    }
    catch (lang::IllegalArgumentException &) {
        throw;
    }
    catch (CommandFailedException &) {
        throw;
    }
    catch (deployment::DeploymentException &) {
        throw;
    }
    catch (Exception &) {
        Any exc( ::cppu::getCaughtException() );
        throw deployment::DeploymentException(
            OUSTR("Error binding package: ") + url,
            static_cast<OWeakObject *>(this), exc );
    }

    guard.reset();
    ::std::pair< t_string2weakref::iterator, bool > insertion(
        m_bound.insert( t_string2weakref::value_type( url, xNewPackage ) ) );
    if (insertion.second)
    { // first insertion
        OSL_ASSERT( Reference<XInterface>(insertion.first->second)
                    == xNewPackage );
    }
    else
    { // found existing entry
        Reference<deployment::XPackage> xPackage( insertion.first->second );
        if (xPackage.is())
            return xPackage;
        insertion.first->second = xNewPackage;
    }
    guard.clear();
    xNewPackage->addEventListener( this ); // listen for disposing events
    return xNewPackage;
}

//##############################################################################

//______________________________________________________________________________
Package::~Package()
{
}

//______________________________________________________________________________
Package::Package( ::rtl::Reference<PackageRegistryBackend> const & myBackend,
                  OUString const & url,
                  OUString const & name,
                  OUString const & displayName,
                  Reference<deployment::XPackageTypeInfo> const & xPackageType )
    : t_PackageBase( getMutex() ),
      m_myBackend( myBackend ),
      m_url( url ),
      m_name( name ),
      m_displayName( displayName ),
      m_xPackageType( xPackageType )
{
}

//______________________________________________________________________________
void Package::disposing()
{
    m_myBackend.clear();
    WeakComponentImplHelperBase::disposing();
}

//______________________________________________________________________________
void Package::check()
{
    ::osl::MutexGuard guard( getMutex() );
    if (rBHelper.bInDispose || rBHelper.bDisposed) {
        throw lang::DisposedException(
            OUSTR("Package instance has already been disposed!"),
            static_cast<OWeakObject *>(this) );
    }
}

// XComponent
//______________________________________________________________________________
void Package::dispose() throw (RuntimeException)
{
    check();
    WeakComponentImplHelperBase::dispose();
}

//______________________________________________________________________________
void Package::addEventListener(
    Reference<lang::XEventListener> const & xListener ) throw (RuntimeException)
{
    check();
    WeakComponentImplHelperBase::addEventListener( xListener );
}

//______________________________________________________________________________
void Package::removeEventListener(
    Reference<lang::XEventListener> const & xListener ) throw (RuntimeException)
{
    check();
    WeakComponentImplHelperBase::removeEventListener( xListener );
}

// XModifyBroadcaster
//______________________________________________________________________________
void Package::addModifyListener(
    Reference<util::XModifyListener> const & xListener )
    throw (RuntimeException)
{
    check();
    rBHelper.addListener( ::getCppuType( &xListener ), xListener );
}

//______________________________________________________________________________
void Package::removeModifyListener(
    Reference<util::XModifyListener> const & xListener )
    throw (RuntimeException)
{
    check();
    rBHelper.removeListener( ::getCppuType( &xListener ), xListener );
}

//______________________________________________________________________________
void Package::checkAborted(
    ::rtl::Reference<AbortChannel> const & abortChannel )
{
    if (abortChannel.is() && abortChannel->isAborted()) {
        throw CommandAbortedException(
            OUSTR("abort!"), static_cast<OWeakObject *>(this) );
    }
}

// XPackage
//______________________________________________________________________________
Reference<task::XAbortChannel> Package::createAbortChannel()
    throw (RuntimeException)
{
    check();
    return new AbortChannel;
}

//______________________________________________________________________________
sal_Bool Package::isBundle() throw (RuntimeException)
{
    return false; // default
}

::sal_Bool Package::checkPrerequisites(
        const css::uno::Reference< css::task::XAbortChannel >& xAbortChannel,
        const css::uno::Reference< css::ucb::XCommandEnvironment >& xCmdEnv )
        throw (css::deployment::DeploymentException,
            css::ucb::CommandFailedException,
            css::ucb::CommandAbortedException,
            css::uno::RuntimeException)
{
    return true;
}

//______________________________________________________________________________
Sequence< Reference<deployment::XPackage> > Package::getBundle(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException,
           lang::IllegalArgumentException, RuntimeException)
{
    return Sequence< Reference<deployment::XPackage> >();
}

//______________________________________________________________________________
OUString Package::getName() throw (RuntimeException)
{
    return m_name;
}

//______________________________________________________________________________
OUString Package::getURL() throw (RuntimeException)
{
    return m_url;
}

//______________________________________________________________________________
OUString Package::getDisplayName() throw (RuntimeException)
{
    return m_displayName;
}

//______________________________________________________________________________
OUString Package::getDescription() throw (RuntimeException)
{
    if (m_xPackageType.is())
        return m_xPackageType->getDescription();
    else
        return OUString();
}

//______________________________________________________________________________
Reference<deployment::XPackageTypeInfo> Package::getPackageType()
    throw (RuntimeException)
{
    return m_xPackageType;
}

//______________________________________________________________________________
void Package::exportTo(
    OUString const & destFolderURL, OUString const & newTitle,
    sal_Int32 nameClashAction, Reference<XCommandEnvironment> const & xCmdEnv )
    throw (CommandFailedException, CommandAbortedException, RuntimeException)
{
    ::ucb::Content destFolder( destFolderURL, xCmdEnv );
    ::ucb::Content sourceContent( getURL(), xCmdEnv );
    if (! destFolder.transferContent(
            sourceContent, ::ucb::InsertOperation_COPY,
            newTitle, nameClashAction ))
        throw RuntimeException( OUSTR("UCB transferContent() failed!"), 0 );
}

//______________________________________________________________________________
void Package::fireModified()
{
    ::cppu::OInterfaceContainerHelper * container = rBHelper.getContainer(
        ::getCppuType( static_cast<Reference<
                       util::XModifyListener> const *>(0) ) );
    if (container != 0) {
        Sequence< Reference<XInterface> > elements(
            container->getElements() );
        lang::EventObject evt( static_cast<OWeakObject *>(this) );
        for ( sal_Int32 pos = 0; pos < elements.getLength(); ++pos )
        {
            Reference<util::XModifyListener> xListener(
                elements[ pos ], UNO_QUERY );
            if (xListener.is())
                xListener->modified( evt );
        }
    }
}

// XPackage
//______________________________________________________________________________
beans::Optional< beans::Ambiguous<sal_Bool> > Package::isRegistered(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException, RuntimeException)
{
    try {
        ::osl::ResettableMutexGuard guard( getMutex() );
        return isRegistered_( guard,
                              AbortChannel::get(xAbortChannel),
                              xCmdEnv );
    }
    catch (RuntimeException &) {
        throw;
    }
    catch (CommandFailedException &) {
        throw;
    }
    catch (CommandAbortedException &) {
        throw;
    }
    catch (deployment::DeploymentException &) {
        throw;
    }
    catch (Exception &) {
        Any exc( ::cppu::getCaughtException() );
        throw deployment::DeploymentException(
            OUSTR("unexpected exception occured!"),
            static_cast<OWeakObject *>(this), exc );
    }
}

//______________________________________________________________________________
void Package::processPackage_(
    bool registerPackage,
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
{
    check();
    bool action = false;

    try {
        try {
            ::osl::ResettableMutexGuard guard( getMutex() );
            beans::Optional< beans::Ambiguous<sal_Bool> > option(
                isRegistered_( guard, AbortChannel::get(xAbortChannel),
                               xCmdEnv ) );
            action = (option.IsPresent &&
                      (option.Value.IsAmbiguous ||
                       (registerPackage ? !option.Value.Value
                                        : option.Value.Value)));
            if (action) {
                OUString displayName( getDisplayName() );
                ProgressLevel progress(
                    xCmdEnv,
                    (registerPackage
                     ? PackageRegistryBackend::StrRegisteringPackage::get()
                     : PackageRegistryBackend::StrRevokingPackage::get())
                    + displayName );
                processPackage_( guard,
                                 registerPackage,
                                 AbortChannel::get(xAbortChannel),
                                 xCmdEnv );
            }
        }
        catch (RuntimeException &) {
            OSL_ENSURE( 0, "### unexpected RuntimeException!" );
            throw;
        }
        catch (CommandFailedException &) {
            throw;
        }
        catch (CommandAbortedException &) {
            throw;
        }
        catch (deployment::DeploymentException &) {
            throw;
        }
        catch (Exception &) {
            Any exc( ::cppu::getCaughtException() );
            throw deployment::DeploymentException(
                (registerPackage
                 ? getResourceString(RID_STR_ERROR_WHILE_REGISTERING)
                 : getResourceString(RID_STR_ERROR_WHILE_REVOKING))
                + getDisplayName(), static_cast<OWeakObject *>(this), exc );
        }
    }
    catch (...) {
        if (action)
            fireModified();
        throw;
    }
    if (action)
        fireModified();
}

//______________________________________________________________________________
void Package::registerPackage(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException,
           lang::IllegalArgumentException, RuntimeException)
{
    processPackage_( true /* register */, xAbortChannel, xCmdEnv );
}

//______________________________________________________________________________
void Package::revokePackage(
    Reference<task::XAbortChannel> const & xAbortChannel,
    Reference<XCommandEnvironment> const & xCmdEnv )
    throw (deployment::DeploymentException,
           CommandFailedException, CommandAbortedException,
           lang::IllegalArgumentException, RuntimeException)
{
    processPackage_( false /* revoke */, xAbortChannel, xCmdEnv );
}

//##############################################################################

//______________________________________________________________________________
Package::TypeInfo::~TypeInfo()
{
}

// XPackageTypeInfo
//______________________________________________________________________________
OUString Package::TypeInfo::getMediaType() throw (RuntimeException)
{
    return m_mediaType;
}

//______________________________________________________________________________
OUString Package::TypeInfo::getDescription() throw (RuntimeException)
{
    return getShortDescription();
}

//______________________________________________________________________________
OUString Package::TypeInfo::getShortDescription() throw (RuntimeException)
{
    return m_shortDescr;
}

//______________________________________________________________________________
OUString Package::TypeInfo::getFileFilter() throw (RuntimeException)
{
    return m_fileFilter;
}

//______________________________________________________________________________
Any Package::TypeInfo::getIcon( sal_Bool highContrast, sal_Bool smallIcon )
    throw (RuntimeException)
{
    if (! smallIcon)
        return Any();
    const sal_uInt16 nIconId = (highContrast ? m_smallIcon_HC : m_smallIcon);
    return Any( &nIconId, getCppuType( static_cast<sal_uInt16 const *>(0) ) );
}

}
}

<|endoftext|>