<commit_before>#include "StableHeaders.h"
#include "EC_ParticleSystem.h"
#include "ModuleInterface.h"
#include "Entity.h"
#include "Renderer.h"
#include "EC_OgrePlaceable.h"
#include "OgreParticleResource.h"
#include "SceneManager.h"
#include "OgreRenderingModule.h"
#include "RexUUID.h"

#include "LoggingFunctions.h"

DEFINE_POCO_LOGGING_FUNCTIONS("EC_ParticleSystem")

#include <Ogre.h>

EC_ParticleSystem::EC_ParticleSystem(Foundation::ModuleInterface *module):
    Foundation::ComponentInterface(module->GetFramework()),
    framework_(module->GetFramework()),
    particleSystem_(0),
    particle_tag_(0),
    particleId_(this, "Particle id"),
    castShadows_(this, "Cast shadows", false),
    renderingDistance_(this, "Rendering distance", 0.0f)
{
    OgreRenderer::OgreRenderingModule *rendererModule = framework_->GetModuleManager()->GetModule<OgreRenderer::OgreRenderingModule>().lock().get();
    if(!rendererModule)
        return;
    renderer_ = OgreRenderer::RendererWeakPtr(rendererModule->GetRenderer());

    QObject::connect(this, SIGNAL(ParentEntitySet()), this, SLOT(UpdateSignals()));
}

EC_ParticleSystem::~EC_ParticleSystem()
{
    DeleteParticleSystem();
}

Foundation::ComponentPtr EC_ParticleSystem::GetPlaceable() const
{
    return placeable_;
}

void EC_ParticleSystem::SetPlaceable(Foundation::ComponentPtr comp)
{
    placeable_ = comp;
}

bool EC_ParticleSystem::HandleResourceEvent(event_id_t event_id, Foundation::EventDataInterface* data)
{
    if (event_id != Resource::Events::RESOURCE_READY)
        return false;

    Resource::Events::ResourceReady* event_data = checked_static_cast<Resource::Events::ResourceReady*>(data);
    if(!event_data)
        return false;

    if (particle_tag_ != event_data->tag_)
        return false;
    particle_tag_ = 0;

    OgreRenderer::OgreParticleResource* partres = checked_static_cast<OgreRenderer::OgreParticleResource*>(event_data->resource_.get());
    if(!partres)
        return false;

    if(partres->GetNumTemplates())
        CreateParticleSystem(QString::fromStdString(partres->GetTemplateName(0)));
}

void EC_ParticleSystem::CreateParticleSystem(const QString &systemName)
{
    if (renderer_.expired())
        return;
    OgreRenderer::RendererPtr renderer = renderer_.lock();

    try
    {
        DeleteParticleSystem();
        Ogre::SceneManager* scene_mgr = renderer->GetSceneManager();
        particleSystem_ = scene_mgr->createParticleSystem(renderer->GetUniqueObjectName(), systemName.toStdString());
        if(particleSystem_)
        {
            OgreRenderer::EC_OgrePlaceable *placeable = dynamic_cast<OgreRenderer::EC_OgrePlaceable *>(placeable_.get());
            if(!placeable)
                return;
            placeable->GetSceneNode()->attachObject(particleSystem_);
            particleSystem_->setCastShadows(castShadows_.Get());
            particleSystem_->setRenderingDistance(renderingDistance_.Get());
            return;
        }
    }
    catch (Ogre::Exception& e)
    {
        LogError("Could not add particle system " + Name().toStdString() + ": " + std::string(e.what()));
    }

    return;
}

void EC_ParticleSystem::DeleteParticleSystem()
{
    if (renderer_.expired() || !particleSystem_)
        return;
    OgreRenderer::RendererPtr renderer = renderer_.lock();

    OgreRenderer::EC_OgrePlaceable *placeable = dynamic_cast<OgreRenderer::EC_OgrePlaceable *>(placeable_.get());
    if(!placeable)
        return;

    Ogre::SceneManager* scene_mgr = renderer->GetSceneManager();
    if(!scene_mgr)
        return;

    try
    {
        //placeable->GetSceneNode()->detachObject(particleSystem_);
        Ogre::SceneNode *node = placeable->GetSceneNode();
        if(!node)
            return;
        node->detachObject(particleSystem_);
    }
    catch (Ogre::Exception& e)
    {
        LogError("Could not delete particle system " + Name().toStdString() + ": " + std::string(e.what()));
    }

    scene_mgr->destroyParticleSystem(particleSystem_);
    particleSystem_ = 0;

    return;
}

void EC_ParticleSystem::AttributeUpdated(Foundation::ComponentInterface *component, Foundation::AttributeInterface *attribute)
{
    if(component != this)
        return;

    if(attribute->GetNameString() == particleId_.GetNameString())
    {
        /*if(particle_tag_)
            return;*/
        Foundation::Attribute<std::string> *particleAtt = dynamic_cast<Foundation::Attribute<std::string> *>(attribute);
        if(!particleAtt)
            return;
        particle_tag_ = RequestResource(particleAtt->Get(), OgreRenderer::OgreParticleResource::GetTypeStatic());
        if(!particle_tag_) // To visualize that resource id was wrong delete previous particle effect off.
            DeleteParticleSystem();
    }
    else if(attribute->GetNameString() == castShadows_.GetNameString())
    {
        if(particleSystem_)
            particleSystem_->setCastShadows(castShadows_.Get());
    }
    else if(attribute->GetNameString() == renderingDistance_.GetNameString())
    {
        if(particleSystem_)
            particleSystem_->setRenderingDistance(renderingDistance_.Get());
    }
}

void EC_ParticleSystem::UpdateSignals()
{
    disconnect(this, SLOT(AttributeUpdated(Foundation::ComponentInterface *, Foundation::AttributeInterface *)));
    FindPlaceable();
    connect(GetParentEntity()->GetScene(), SIGNAL(AttributeChanged(Foundation::ComponentInterface*, Foundation::AttributeInterface*, AttributeChange::Type)),
            this, SLOT(AttributeUpdated(Foundation::ComponentInterface*, Foundation::AttributeInterface*)));
}

void EC_ParticleSystem::FindPlaceable()
{
    assert(framework_);
    Scene::ScenePtr scene = framework_->GetDefaultWorldScene();
    placeable_ = GetParentEntity()->GetComponent<OgreRenderer::EC_OgrePlaceable>();
    if(!placeable_)
        LogError("Couldn't find a EC_OgrePlaceable coponent in this entity.");
    return;
}

request_tag_t EC_ParticleSystem::RequestResource(const std::string& id, const std::string& type)
{
    request_tag_t tag = 0;
    if(renderer_.expired())
        return tag;

    tag = renderer_.lock()->RequestResource(id, type);
    if(tag == 0)
    {
        LogWarning("Failed to request resource:" + id + " : " + type);
        return 0;
    }

    return tag;
}<commit_msg>Fix "warning C4715: 'EC_ParticleSystem::HandleResourceEvent' : not all control paths return a value"<commit_after>#include "StableHeaders.h"
#include "EC_ParticleSystem.h"
#include "ModuleInterface.h"
#include "Entity.h"
#include "Renderer.h"
#include "EC_OgrePlaceable.h"
#include "OgreParticleResource.h"
#include "SceneManager.h"
#include "OgreRenderingModule.h"
#include "RexUUID.h"

#include "LoggingFunctions.h"

DEFINE_POCO_LOGGING_FUNCTIONS("EC_ParticleSystem")

#include <Ogre.h>

EC_ParticleSystem::EC_ParticleSystem(Foundation::ModuleInterface *module):
    Foundation::ComponentInterface(module->GetFramework()),
    framework_(module->GetFramework()),
    particleSystem_(0),
    particle_tag_(0),
    particleId_(this, "Particle id"),
    castShadows_(this, "Cast shadows", false),
    renderingDistance_(this, "Rendering distance", 0.0f)
{
    OgreRenderer::OgreRenderingModule *rendererModule = framework_->GetModuleManager()->GetModule<OgreRenderer::OgreRenderingModule>().lock().get();
    if(!rendererModule)
        return;
    renderer_ = OgreRenderer::RendererWeakPtr(rendererModule->GetRenderer());

    QObject::connect(this, SIGNAL(ParentEntitySet()), this, SLOT(UpdateSignals()));
}

EC_ParticleSystem::~EC_ParticleSystem()
{
    DeleteParticleSystem();
}

Foundation::ComponentPtr EC_ParticleSystem::GetPlaceable() const
{
    return placeable_;
}

void EC_ParticleSystem::SetPlaceable(Foundation::ComponentPtr comp)
{
    placeable_ = comp;
}

bool EC_ParticleSystem::HandleResourceEvent(event_id_t event_id, Foundation::EventDataInterface* data)
{
    Resource::Events::ResourceReady* event_data = checked_static_cast<Resource::Events::ResourceReady*>(data);
    if (event_id != Resource::Events::RESOURCE_READY || !event_data || particle_tag_ != event_data->tag_)
        return false;

    OgreRenderer::OgreParticleResource* partres = checked_static_cast<OgreRenderer::OgreParticleResource*>(event_data->resource_.get());
    if (!partres)
        return false;

    if (partres->GetNumTemplates())
        CreateParticleSystem(QString::fromStdString(partres->GetTemplateName(0)));

    return false;
}

void EC_ParticleSystem::CreateParticleSystem(const QString &systemName)
{
    if (renderer_.expired())
        return;
    OgreRenderer::RendererPtr renderer = renderer_.lock();

    try
    {
        DeleteParticleSystem();
        Ogre::SceneManager* scene_mgr = renderer->GetSceneManager();
        particleSystem_ = scene_mgr->createParticleSystem(renderer->GetUniqueObjectName(), systemName.toStdString());
        if(particleSystem_)
        {
            OgreRenderer::EC_OgrePlaceable *placeable = dynamic_cast<OgreRenderer::EC_OgrePlaceable *>(placeable_.get());
            if(!placeable)
                return;
            placeable->GetSceneNode()->attachObject(particleSystem_);
            particleSystem_->setCastShadows(castShadows_.Get());
            particleSystem_->setRenderingDistance(renderingDistance_.Get());
            return;
        }
    }
    catch (Ogre::Exception& e)
    {
        LogError("Could not add particle system " + Name().toStdString() + ": " + std::string(e.what()));
    }

    return;
}

void EC_ParticleSystem::DeleteParticleSystem()
{
    if (renderer_.expired() || !particleSystem_)
        return;
    OgreRenderer::RendererPtr renderer = renderer_.lock();

    OgreRenderer::EC_OgrePlaceable *placeable = dynamic_cast<OgreRenderer::EC_OgrePlaceable *>(placeable_.get());
    if(!placeable)
        return;

    Ogre::SceneManager* scene_mgr = renderer->GetSceneManager();
    if(!scene_mgr)
        return;

    try
    {
        //placeable->GetSceneNode()->detachObject(particleSystem_);
        Ogre::SceneNode *node = placeable->GetSceneNode();
        if(!node)
            return;
        node->detachObject(particleSystem_);
    }
    catch (Ogre::Exception& e)
    {
        LogError("Could not delete particle system " + Name().toStdString() + ": " + std::string(e.what()));
    }

    scene_mgr->destroyParticleSystem(particleSystem_);
    particleSystem_ = 0;

    return;
}

void EC_ParticleSystem::AttributeUpdated(Foundation::ComponentInterface *component, Foundation::AttributeInterface *attribute)
{
    if(component != this)
        return;

    if(attribute->GetNameString() == particleId_.GetNameString())
    {
        /*if(particle_tag_)
            return;*/
        Foundation::Attribute<std::string> *particleAtt = dynamic_cast<Foundation::Attribute<std::string> *>(attribute);
        if(!particleAtt)
            return;
        particle_tag_ = RequestResource(particleAtt->Get(), OgreRenderer::OgreParticleResource::GetTypeStatic());
        if(!particle_tag_) // To visualize that resource id was wrong delete previous particle effect off.
            DeleteParticleSystem();
    }
    else if(attribute->GetNameString() == castShadows_.GetNameString())
    {
        if(particleSystem_)
            particleSystem_->setCastShadows(castShadows_.Get());
    }
    else if(attribute->GetNameString() == renderingDistance_.GetNameString())
    {
        if(particleSystem_)
            particleSystem_->setRenderingDistance(renderingDistance_.Get());
    }
}

void EC_ParticleSystem::UpdateSignals()
{
    disconnect(this, SLOT(AttributeUpdated(Foundation::ComponentInterface *, Foundation::AttributeInterface *)));
    FindPlaceable();
    connect(GetParentEntity()->GetScene(), SIGNAL(AttributeChanged(Foundation::ComponentInterface*, Foundation::AttributeInterface*, AttributeChange::Type)),
            this, SLOT(AttributeUpdated(Foundation::ComponentInterface*, Foundation::AttributeInterface*)));
}

void EC_ParticleSystem::FindPlaceable()
{
    assert(framework_);
    Scene::ScenePtr scene = framework_->GetDefaultWorldScene();
    placeable_ = GetParentEntity()->GetComponent<OgreRenderer::EC_OgrePlaceable>();
    if(!placeable_)
        LogError("Couldn't find a EC_OgrePlaceable coponent in this entity.");
    return;
}

request_tag_t EC_ParticleSystem::RequestResource(const std::string& id, const std::string& type)
{
    request_tag_t tag = 0;
    if(renderer_.expired())
        return tag;

    tag = renderer_.lock()->RequestResource(id, type);
    if(tag == 0)
    {
        LogWarning("Failed to request resource:" + id + " : " + type);
        return 0;
    }

    return tag;
}<|endoftext|>


<commit_before>#include "math.hpp"
#include "util.hpp"
#include "muglm/matrix_helper.hpp"
#include "muglm/muglm_impl.hpp"
#include "memory_mapped_texture.hpp"

using namespace muglm;
using namespace Granite;
using namespace Granite::SceneFormats;

// Shameless copy-pasta from learnopengl.com. :)

static float RadicalInverse_VdC(uint32_t bits)
{
	bits = (bits << 16u) | (bits >> 16u);
	bits = ((bits & 0x55555555u) << 1u) | ((bits & 0xAAAAAAAAu) >> 1u);
	bits = ((bits & 0x33333333u) << 2u) | ((bits & 0xCCCCCCCCu) >> 2u);
	bits = ((bits & 0x0F0F0F0Fu) << 4u) | ((bits & 0xF0F0F0F0u) >> 4u);
	bits = ((bits & 0x00FF00FFu) << 8u) | ((bits & 0xFF00FF00u) >> 8u);
	return float(bits) * 2.3283064365386963e-10f; // / 0x100000000
}

static vec2 Hammersley(uint i, uint N)
{
	return vec2(float(i) / float(N), RadicalInverse_VdC(i));
}

static vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness)
{
	float a = roughness * roughness;

	float phi = 2.0f * pi<float>() * Xi.x;
	float cosTheta = sqrt((1.0f - Xi.y) / (1.0f + (a * a - 1.0f) * Xi.y));
	float sinTheta = sqrt(1.0f - cosTheta * cosTheta);

	// from spherical coordinates to cartesian coordinates
	vec3 H;
	H.x = cos(phi) * sinTheta;
	H.y = sin(phi) * sinTheta;
	H.z = cosTheta;

	// from tangent-space vector to world-space sample vector
	vec3 up        = abs(N.z) < 0.999f ? vec3(0.0f, 0.0f, 1.0f) : vec3(1.0f, 0.0f, 0.0f);
	vec3 tangent   = normalize(cross(up, N));
	vec3 bitangent = cross(N, tangent);

	vec3 sampleVec = tangent * H.x + bitangent * H.y + N * H.z;
	return normalize(sampleVec);
}

static float GeometrySchlickGGX(float NdotV, float roughness)
{
	float a = roughness;
	float k = (a * a) / 2.0f;

	float nom   = NdotV;
	float denom = NdotV * (1.0f - k) + k;

	return nom / denom;
}

static float GeometrySmith(vec3 N, vec3 V, vec3 L, float roughness)
{
	float NdotV = max(dot(N, V), 0.0f);
	float NdotL = max(dot(N, L), 0.0f);
	float ggx2 = GeometrySchlickGGX(NdotV, roughness);
	float ggx1 = GeometrySchlickGGX(NdotL, roughness);

	return ggx1 * ggx2;
}

static vec2 IntegrateBRDF(float NdotV, float roughness)
{
	vec3 V;
	V.x = sqrt(1.0f - NdotV * NdotV);
	V.y = 0.0f;
	V.z = NdotV;

	float A = 0.0f;
	float B = 0.0f;

	vec3 N = vec3(0.0f, 0.0f, 1.0f);

	const unsigned SAMPLE_COUNT = 1024u;
	for (unsigned i = 0u; i < SAMPLE_COUNT; i++)
	{
		vec2 Xi = Hammersley(i, SAMPLE_COUNT);
		vec3 H  = ImportanceSampleGGX(Xi, N, roughness);
		vec3 L  = normalize(2.0f * dot(V, H) * H - V);

		float NdotL = max(L.z, 0.0f);
		float NdotH = max(H.z, 0.0f);
		float VdotH = max(dot(V, H), 0.0f);

		if (NdotL > 0.0f)
		{
			float G = GeometrySmith(N, V, L, roughness);
			float G_Vis = (G * VdotH) / (NdotH * NdotV);
			float Fc = pow(1.0f - VdotH, 5.0f);

			A += (1.0f - Fc) * G_Vis;
			B += Fc * G_Vis;
		}
	}
	A /= float(SAMPLE_COUNT);
	B /= float(SAMPLE_COUNT);
	return vec2(A, B);
}

int main(int argc, char *argv[])
{
	if (argc != 2)
	{
		LOGE("Usage: %s <output.gtx>\n", argv[0]);
		return 1;
	}

	const unsigned width = 256;
	const unsigned height = 256;

	MemoryMappedTexture tex;
	tex.set_2d(VK_FORMAT_R16G16_SFLOAT, width, height);
	if (!tex.map_write(argv[1]))
	{
		LOGE("Failed to save image to: %s\n", argv[1]);
		return 1;
	}

	for (unsigned y = 0; y < height; y++)
	{
		for (unsigned x = 0; x < width; x++)
		{
			float NoV = (x + 0.5f) * (1.0f / width);
			float roughness = (y + 0.5f) * (1.0f / height);
			//roughness = roughness * 0.75f + 0.25f;
			*tex.get_layout().data_2d<uint32_t>(x, y) = packHalf2x16(IntegrateBRDF(NoV, roughness));
		}
	}
}
<commit_msg>Build fix for MSVC.<commit_after>#include "math.hpp"
#include "util.hpp"
#include "muglm/matrix_helper.hpp"
#include "muglm/muglm_impl.hpp"
#include "memory_mapped_texture.hpp"

using namespace muglm;
using namespace Granite;
using namespace Granite::SceneFormats;

// Shameless copy-pasta from learnopengl.com. :)

static float RadicalInverse_VdC(uint32_t bits)
{
	bits = (bits << 16u) | (bits >> 16u);
	bits = ((bits & 0x55555555u) << 1u) | ((bits & 0xAAAAAAAAu) >> 1u);
	bits = ((bits & 0x33333333u) << 2u) | ((bits & 0xCCCCCCCCu) >> 2u);
	bits = ((bits & 0x0F0F0F0Fu) << 4u) | ((bits & 0xF0F0F0F0u) >> 4u);
	bits = ((bits & 0x00FF00FFu) << 8u) | ((bits & 0xFF00FF00u) >> 8u);
	return float(bits) * 2.3283064365386963e-10f; // / 0x100000000
}

static vec2 Hammersley(uint i, uint N)
{
	return vec2(float(i) / float(N), RadicalInverse_VdC(i));
}

static vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness)
{
	float a = roughness * roughness;

	float phi = 2.0f * pi<float>() * Xi.x;
	float cosTheta = muglm::sqrt((1.0f - Xi.y) / (1.0f + (a * a - 1.0f) * Xi.y));
	float sinTheta = muglm::sqrt(1.0f - cosTheta * cosTheta);

	// from spherical coordinates to cartesian coordinates
	vec3 H;
	H.x = cos(phi) * sinTheta;
	H.y = sin(phi) * sinTheta;
	H.z = cosTheta;

	// from tangent-space vector to world-space sample vector
	vec3 up        = abs(N.z) < 0.999f ? vec3(0.0f, 0.0f, 1.0f) : vec3(1.0f, 0.0f, 0.0f);
	vec3 tangent   = normalize(cross(up, N));
	vec3 bitangent = cross(N, tangent);

	vec3 sampleVec = tangent * H.x + bitangent * H.y + N * H.z;
	return normalize(sampleVec);
}

static float GeometrySchlickGGX(float NdotV, float roughness)
{
	float a = roughness;
	float k = (a * a) / 2.0f;

	float nom   = NdotV;
	float denom = NdotV * (1.0f - k) + k;

	return nom / denom;
}

static float GeometrySmith(vec3 N, vec3 V, vec3 L, float roughness)
{
	float NdotV = max(dot(N, V), 0.0f);
	float NdotL = max(dot(N, L), 0.0f);
	float ggx2 = GeometrySchlickGGX(NdotV, roughness);
	float ggx1 = GeometrySchlickGGX(NdotL, roughness);

	return ggx1 * ggx2;
}

static vec2 IntegrateBRDF(float NdotV, float roughness)
{
	vec3 V;
	V.x = muglm::sqrt(1.0f - NdotV * NdotV);
	V.y = 0.0f;
	V.z = NdotV;

	float A = 0.0f;
	float B = 0.0f;

	vec3 N = vec3(0.0f, 0.0f, 1.0f);

	const unsigned SAMPLE_COUNT = 1024u;
	for (unsigned i = 0u; i < SAMPLE_COUNT; i++)
	{
		vec2 Xi = Hammersley(i, SAMPLE_COUNT);
		vec3 H  = ImportanceSampleGGX(Xi, N, roughness);
		vec3 L  = normalize(2.0f * dot(V, H) * H - V);

		float NdotL = max(L.z, 0.0f);
		float NdotH = max(H.z, 0.0f);
		float VdotH = max(dot(V, H), 0.0f);

		if (NdotL > 0.0f)
		{
			float G = GeometrySmith(N, V, L, roughness);
			float G_Vis = (G * VdotH) / (NdotH * NdotV);
			float Fc = pow(1.0f - VdotH, 5.0f);

			A += (1.0f - Fc) * G_Vis;
			B += Fc * G_Vis;
		}
	}
	A /= float(SAMPLE_COUNT);
	B /= float(SAMPLE_COUNT);
	return vec2(A, B);
}

int main(int argc, char *argv[])
{
	if (argc != 2)
	{
		LOGE("Usage: %s <output.gtx>\n", argv[0]);
		return 1;
	}

	const unsigned width = 256;
	const unsigned height = 256;

	MemoryMappedTexture tex;
	tex.set_2d(VK_FORMAT_R16G16_SFLOAT, width, height);
	if (!tex.map_write(argv[1]))
	{
		LOGE("Failed to save image to: %s\n", argv[1]);
		return 1;
	}

	for (unsigned y = 0; y < height; y++)
	{
		for (unsigned x = 0; x < width; x++)
		{
			float NoV = (x + 0.5f) * (1.0f / width);
			float roughness = (y + 0.5f) * (1.0f / height);
			//roughness = roughness * 0.75f + 0.25f;
			*tex.get_layout().data_2d<uint32_t>(x, y) = packHalf2x16(IntegrateBRDF(NoV, roughness));
		}
	}
}
<|endoftext|>


<commit_before>/*
 * SessionBuildEnvironment.cpp
 *
 * Copyright (C) 2009-12 by RStudio, Inc.
 *
 * Unless you have received this program directly from RStudio pursuant
 * to the terms of a commercial license agreement with RStudio, then
 * this program is licensed to you under the terms of version 3 of the
 * GNU Affero General Public License. This program is distributed WITHOUT
 * ANY EXPRESS OR IMPLIED WARRANTY, INCLUDING THOSE OF NON-INFRINGEMENT,
 * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Please refer to the
 * AGPL (http://www.gnu.org/licenses/agpl-3.0.txt) for more details.
 *
 */

#include "SessionBuildEnvironment.hpp"

#include <string>
#include <vector>

#include <boost/regex.hpp>
#include <boost/format.hpp>

#include <core/Error.hpp>
#include <core/FilePath.hpp>

#include <core/FileSerializer.hpp>
#include <core/system/System.hpp>
#include <core/r_util/RToolsInfo.hpp>

#include <r/RExec.hpp>

#include <session/SessionModuleContext.hpp>

using namespace core ;

namespace session {
namespace modules {
namespace build {

#ifdef _WIN32

namespace {

r_util::RToolsInfo scanPathForRTools()
{
   // first confirm ls.exe is in Rtools
   r_util::RToolsInfo noToolsFound;
   FilePath lsPath = module_context::findProgram("ls.exe");
   if (lsPath.empty())
      return noToolsFound;

   // we have a candidate installPath
   FilePath installPath = lsPath.parent().parent();
   core::system::ensureLongPath(&installPath);
   if (!installPath.childPath("Rtools.txt").exists())
      return noToolsFound;

   // find the version path
   FilePath versionPath = installPath.childPath("VERSION.txt");
   if (!versionPath.exists())
      return noToolsFound;

   // further verify that gcc is in Rtools
   FilePath gccPath = module_context::findProgram("gcc.exe");
   if (!gccPath.exists())
      return noToolsFound;
   if (!gccPath.parent().parent().parent().childPath("Rtools.txt").exists())
      return noToolsFound;

   // Rtools is in the path -- now crack the VERSION file
   std::string contents;
   Error error = core::readStringFromFile(versionPath, &contents);
   if (error)
   {
      LOG_ERROR(error);
      return noToolsFound;
   }

   // extract the version
   boost::algorithm::trim(contents);
   boost::regex pattern("Rtools version (\\d\\.\\d\\d)[\\d\\.]+$");
   boost::smatch match;
   if (boost::regex_search(contents, match, pattern))
      return r_util::RToolsInfo(match[1], installPath);
   else
      return noToolsFound;
}

std::string formatPath(const FilePath& filePath)
{
   FilePath displayPath = filePath;
   core::system::ensureLongPath(&displayPath);
   return boost::algorithm::replace_all_copy(
                                 displayPath.absolutePath(), "/", "\\");
}

template <typename T>
bool doAddRtoolsToPathIfNecessary(T* pTarget, std::string* pWarningMessage)
{
    // can we find ls.exe and gcc.exe on the path? if so then
    // we assume Rtools are already there (this is the same test
    // used by devtools)
    bool rToolsOnPath = false;
    Error error = r::exec::RFunction(".rs.isRtoolsOnPath").call(&rToolsOnPath);
    if (error)
       LOG_ERROR(error);
    if (rToolsOnPath)
    {
       // perform an extra check to see if the version on the path is not
       // compatible with the currenly running version of R
       r_util::RToolsInfo rTools = scanPathForRTools();
       if (!rTools.empty())
       {
          if (!isRtoolsCompatible(rTools))
          {
            boost::format fmt(
             "WARNING: Rtools version %1% is on the PATH (intalled at %2%) "
             "but is "
             "not compatible with the currently running version of R."
             "\n\nPlease download and install the appropriate version of "
             "Rtools to ensure that packages are built correctly:"
             "\n\nhttp://cran.rstudio.com/bin/windows/Rtools/"
             "\n\nNote that in addition to installing a compatible verison you "
             "also need to remove the incompatible version from your PATH");
            *pWarningMessage = boost::str(
               fmt % rTools.name() % formatPath(rTools.installPath()));
          }
       }

       return false;
    }

    // ok so scan for R tools
    std::vector<r_util::RToolsInfo> rTools;
    error = core::r_util::scanRegistryForRTools(&rTools);
    if (error)
    {
       LOG_ERROR(error);
       return false;
    }

    // enumerate them to see if we have a compatible version
    // (go in reverse order for most recent first)
    std::vector<r_util::RToolsInfo>::const_reverse_iterator it = rTools.rbegin();
    for ( ; it != rTools.rend(); ++it)
    {
       if (isRtoolsCompatible(*it))
       {
          r_util::prependToSystemPath(*it, pTarget);
          return true;
       }
    }

    // if we found no version of rtools whatsoever then print warning and return
    if (rTools.empty())
    {
       *pWarningMessage =
           "WARNING: Rtools is required to build R packages but is not "
           "currently installed. "
           "Please download and install the appropriate "
           "version of Rtools before proceeding:\n\n"
           "http://cran.rstudio.com/bin/windows/Rtools/";
    }
    else
    {
       // Rtools installed but no compatible version, print a suitable warning
       pWarningMessage->append(
          "WARNING: Rtools is required to build R packages but no version "
          "of Rtools compatible with the currently running version of R "
          "was found. Note that the following incompatible version(s) "
          "of Rtools were found:\n\n");

       std::vector<r_util::RToolsInfo>::const_iterator fwdIt = rTools.begin();
       for (; fwdIt != rTools.end(); ++fwdIt)
       {
          std::string path = formatPath(fwdIt->installPath());
          boost::format fmt("  - Rtools %1% (installed at %2%)\n");
          pWarningMessage->append(boost::str(fmt % fwdIt->name() % path));
       }

       pWarningMessage->append(
          "\nPlease download and install the appropriate "
          "version of Rtools before proceeding:\n\n"
          "http://cran.rstudio.com/bin/windows/Rtools/");
    }

    return false;
}

} // anonymous namespace

bool isRtoolsCompatible(const r_util::RToolsInfo& rTools)
{
   bool isCompatible = false;
   Error error = r::exec::evaluateString(rTools.versionPredicate(),
                                         &isCompatible);
   if (error)
      LOG_ERROR(error);
   return isCompatible;
}

bool addRtoolsToPathIfNecessary(std::string* pPath,
                                std::string* pWarningMessage)
{
   return doAddRtoolsToPathIfNecessary(pPath, pWarningMessage);
}

bool addRtoolsToPathIfNecessary(core::system::Options* pEnvironment,
                                std::string* pWarningMessage)
{
   return doAddRtoolsToPathIfNecessary(pEnvironment, pWarningMessage);
}

#else

bool isRtoolsCompatible(const r_util::RToolsInfo& rTools)
{
   return false;
}

bool addRtoolsToPathIfNecessary(std::string* pPath,
                                std::string* pWarningMessage)
{
   return false;
}

bool addRtoolsToPathIfNecessary(core::system::Options* pEnvironment,
                                std::string* pWarningMessage)
{
   return false;
}

#endif

} // namespace build
} // namespace modules
} // namespace session
<commit_msg>always use Rtools for windows build functions (never use what's on the PATH)<commit_after>/*
 * SessionBuildEnvironment.cpp
 *
 * Copyright (C) 2009-12 by RStudio, Inc.
 *
 * Unless you have received this program directly from RStudio pursuant
 * to the terms of a commercial license agreement with RStudio, then
 * this program is licensed to you under the terms of version 3 of the
 * GNU Affero General Public License. This program is distributed WITHOUT
 * ANY EXPRESS OR IMPLIED WARRANTY, INCLUDING THOSE OF NON-INFRINGEMENT,
 * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Please refer to the
 * AGPL (http://www.gnu.org/licenses/agpl-3.0.txt) for more details.
 *
 */

#include "SessionBuildEnvironment.hpp"

#include <string>
#include <vector>

#include <boost/regex.hpp>
#include <boost/format.hpp>

#include <core/Error.hpp>
#include <core/FilePath.hpp>

#include <core/FileSerializer.hpp>
#include <core/system/System.hpp>
#include <core/r_util/RToolsInfo.hpp>

#include <r/RExec.hpp>

#include <session/SessionModuleContext.hpp>

using namespace core ;

namespace session {
namespace modules {
namespace build {

#ifdef _WIN32

namespace {

r_util::RToolsInfo scanPathForRTools()
{
   // first confirm ls.exe is in Rtools
   r_util::RToolsInfo noToolsFound;
   FilePath lsPath = module_context::findProgram("ls.exe");
   if (lsPath.empty())
      return noToolsFound;

   // we have a candidate installPath
   FilePath installPath = lsPath.parent().parent();
   core::system::ensureLongPath(&installPath);
   if (!installPath.childPath("Rtools.txt").exists())
      return noToolsFound;

   // find the version path
   FilePath versionPath = installPath.childPath("VERSION.txt");
   if (!versionPath.exists())
      return noToolsFound;

   // further verify that gcc is in Rtools
   FilePath gccPath = module_context::findProgram("gcc.exe");
   if (!gccPath.exists())
      return noToolsFound;
   if (!gccPath.parent().parent().parent().childPath("Rtools.txt").exists())
      return noToolsFound;

   // Rtools is in the path -- now crack the VERSION file
   std::string contents;
   Error error = core::readStringFromFile(versionPath, &contents);
   if (error)
   {
      LOG_ERROR(error);
      return noToolsFound;
   }

   // extract the version
   boost::algorithm::trim(contents);
   boost::regex pattern("Rtools version (\\d\\.\\d\\d)[\\d\\.]+$");
   boost::smatch match;
   if (boost::regex_search(contents, match, pattern))
      return r_util::RToolsInfo(match[1], installPath);
   else
      return noToolsFound;
}

std::string formatPath(const FilePath& filePath)
{
   FilePath displayPath = filePath;
   core::system::ensureLongPath(&displayPath);
   return boost::algorithm::replace_all_copy(
                                 displayPath.absolutePath(), "/", "\\");
}

template <typename T>
bool doAddRtoolsToPathIfNecessary(T* pTarget, std::string* pWarningMessage)
{
    // ok so scan for R tools
    std::vector<r_util::RToolsInfo> rTools;
    Error error = core::r_util::scanRegistryForRTools(&rTools);
    if (error)
    {
       LOG_ERROR(error);
       return false;
    }

    // enumerate them to see if we have a compatible version
    // (go in reverse order for most recent first)
    std::vector<r_util::RToolsInfo>::const_reverse_iterator it = rTools.rbegin();
    for ( ; it != rTools.rend(); ++it)
    {
       if (isRtoolsCompatible(*it))
       {
          r_util::prependToSystemPath(*it, pTarget);
          return true;
       }
    }

    // if we found no version of rtools whatsoever then print warning and return
    if (rTools.empty())
    {
       *pWarningMessage =
           "WARNING: Rtools is required to build R packages but is not "
           "currently installed. "
           "Please download and install the appropriate "
           "version of Rtools before proceeding:\n\n"
           "http://cran.rstudio.com/bin/windows/Rtools/";
    }
    else
    {
       // Rtools installed but no compatible version, print a suitable warning
       pWarningMessage->append(
          "WARNING: Rtools is required to build R packages but no version "
          "of Rtools compatible with the currently running version of R "
          "was found. Note that the following incompatible version(s) "
          "of Rtools were found:\n\n");

       std::vector<r_util::RToolsInfo>::const_iterator fwdIt = rTools.begin();
       for (; fwdIt != rTools.end(); ++fwdIt)
       {
          std::string path = formatPath(fwdIt->installPath());
          boost::format fmt("  - Rtools %1% (installed at %2%)\n");
          pWarningMessage->append(boost::str(fmt % fwdIt->name() % path));
       }

       pWarningMessage->append(
          "\nPlease download and install the appropriate "
          "version of Rtools before proceeding:\n\n"
          "http://cran.rstudio.com/bin/windows/Rtools/");
    }

    return false;
}

} // anonymous namespace

bool isRtoolsCompatible(const r_util::RToolsInfo& rTools)
{
   bool isCompatible = false;
   Error error = r::exec::evaluateString(rTools.versionPredicate(),
                                         &isCompatible);
   if (error)
      LOG_ERROR(error);
   return isCompatible;
}

bool addRtoolsToPathIfNecessary(std::string* pPath,
                                std::string* pWarningMessage)
{
   return doAddRtoolsToPathIfNecessary(pPath, pWarningMessage);
}

bool addRtoolsToPathIfNecessary(core::system::Options* pEnvironment,
                                std::string* pWarningMessage)
{
   return doAddRtoolsToPathIfNecessary(pEnvironment, pWarningMessage);
}

#else

bool isRtoolsCompatible(const r_util::RToolsInfo& rTools)
{
   return false;
}

bool addRtoolsToPathIfNecessary(std::string* pPath,
                                std::string* pWarningMessage)
{
   return false;
}

bool addRtoolsToPathIfNecessary(core::system::Options* pEnvironment,
                                std::string* pWarningMessage)
{
   return false;
}

#endif

} // namespace build
} // namespace modules
} // namespace session
<|endoftext|>


<commit_before>/***********************************************************************
    filename:   CEGUIOpenGLGLXPBTextureTarget.cpp
    created:    Sat Jan 31 2009
    author:     Paul D Turner
*************************************************************************/
/***************************************************************************
 *   Copyright (C) 2004 - 2009 Paul D Turner & The CEGUI Development Team
 *
 *   Permission is hereby granted, free of charge, to any person obtaining
 *   a copy of this software and associated documentation files (the
 *   "Software"), to deal in the Software without restriction, including
 *   without limitation the rights to use, copy, modify, merge, publish,
 *   distribute, sublicense, and/or sell copies of the Software, and to
 *   permit persons to whom the Software is furnished to do so, subject to
 *   the following conditions:
 *
 *   The above copyright notice and this permission notice shall be
 *   included in all copies or substantial portions of the Software.
 *
 *   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 *   EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 *   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
 *   IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
 *   OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
 *   ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 *   OTHER DEALINGS IN THE SOFTWARE.
 ***************************************************************************/
#include "CEGUIOpenGLGLXPBTextureTarget.h"
#include "CEGUIExceptions.h"
#include "CEGUIRenderQueue.h"
#include "CEGUIGeometryBuffer.h"

#include "CEGUIOpenGLRenderer.h"
#include "CEGUIOpenGLTexture.h"

#include <iostream>

// Start of CEGUI namespace section
namespace CEGUI
{
//----------------------------------------------------------------------------//
const float OpenGLGLXPBTextureTarget::DEFAULT_SIZE = 128.0f;

//----------------------------------------------------------------------------//
// internal attribute array used to get pbuffer configs
int pbAttrs[] =
{
    GLX_DRAWABLE_TYPE, GLX_PBUFFER_BIT,
    GLX_DOUBLEBUFFER, GL_FALSE,
    GLX_RED_SIZE, 8,
    GLX_GREEN_SIZE, 8,
    GLX_BLUE_SIZE, 8,
    GLX_ALPHA_SIZE, 8,
    None
};

//----------------------------------------------------------------------------//
OpenGLGLXPBTextureTarget::OpenGLGLXPBTextureTarget(OpenGLRenderer& owner) :
    OpenGLTextureTarget(owner),
    d_pbuffer(0)
{
    if (!GLXEW_VERSION_1_3)
        CEGUI_THROW(InvalidRequestException("System does not support GLX >= 1.3 "
            "required by CEGUI pbuffer usage under GLX"));

    d_dpy = glXGetCurrentDisplay();

    selectFBConfig();
    createContext();
    initialiseTexture();

    // set default size (and cause initialisation of the pbuffer)
    declareRenderSize(Size(DEFAULT_SIZE, DEFAULT_SIZE));

    // set some states as a one-time thing (because we use a separate context)
    enablePBuffer();

    glEnable(GL_SCISSOR_TEST);
    glEnable(GL_TEXTURE_2D);
    glEnable(GL_BLEND);
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_COLOR_ARRAY);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
    glDisableClientState(GL_SECONDARY_COLOR_ARRAY);
    glDisableClientState(GL_INDEX_ARRAY);
    glDisableClientState(GL_NORMAL_ARRAY);
    glDisableClientState(GL_FOG_COORDINATE_ARRAY);
    glDisableClientState(GL_EDGE_FLAG_ARRAY);
    glClearColor(0,0,0,0);

    disablePBuffer();
}

//----------------------------------------------------------------------------//
OpenGLGLXPBTextureTarget::~OpenGLGLXPBTextureTarget()
{
    if (d_pbuffer)
        glXDestroyPbuffer(d_dpy, d_pbuffer);
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::activate()
{
    enablePBuffer();

    OpenGLRenderTarget::activate();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::deactivate()
{
    // grab what we rendered into the texture
    glBindTexture(GL_TEXTURE_2D, d_texture);
    glCopyTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8,
                     0, 0,
                     static_cast<GLsizei>(d_area.d_right),
                     static_cast<GLsizei>(d_area.d_bottom), 0);

    disablePBuffer();

    OpenGLRenderTarget::deactivate();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::clear()
{
    enablePBuffer();
    glDisable(GL_SCISSOR_TEST);
    glClear(GL_COLOR_BUFFER_BIT);
    glEnable(GL_SCISSOR_TEST);
    disablePBuffer();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::declareRenderSize(const Size& sz)
{
    // exit if current size is enough
    if ((d_area.getWidth() >= sz.d_width) &&
        (d_area.getHeight() >= sz.d_height))
            return;

    setArea(Rect(d_area.getPosition(), d_owner.getAdjustedTextureSize(sz)));
    initialisePBuffer();
    clear();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::initialisePBuffer()
{
    int creation_attrs[] =
    {
        GLX_PBUFFER_WIDTH, d_area.getWidth(),
        GLX_PBUFFER_HEIGHT, d_area.getHeight(),
        GLX_LARGEST_PBUFFER, True,
        GLX_PRESERVED_CONTENTS, True,
        None
    };

    // release any existing pbuffer
    if (d_pbuffer)
        glXDestroyPbuffer(d_dpy, d_pbuffer);

    d_pbuffer = glXCreatePbuffer(d_dpy, d_fbconfig, creation_attrs);

    if (!d_pbuffer)
        CEGUI_THROW(RendererException(
            "OpenGLGLXPBTextureTarget::initialisePBuffer - "
            "pbuffer creation error:  glXCreatePbuffer() failed"));

    // get the real size of the buffer that was created
    GLuint actual_width, actual_height;
    glXQueryDrawable(d_dpy, d_pbuffer, GLX_WIDTH, &actual_width);
    glXQueryDrawable(d_dpy, d_pbuffer, GLX_HEIGHT, &actual_height);
    d_area.setSize(Size(actual_width, actual_height));

    // ensure CEGUI::Texture is wrapping real GL texture and has correct size
    d_CEGUITexture->setOpenGLTexture(d_texture, d_area.getSize());
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::enablePBuffer() const
{
    // switch to using the pbuffer
    d_prevDisplay = glXGetCurrentDisplay();
    d_prevDrawable = glXGetCurrentDrawable();
    d_prevContext = glXGetCurrentContext();

    if (!glXMakeCurrent(d_dpy, d_pbuffer, d_context))
        std::cerr << "Failed to switch to pbuffer for rendering" << std::endl;
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::disablePBuffer() const
{
    // switch back to rendering to previous set up
    if (!glXMakeCurrent(d_prevDisplay, d_prevDrawable, d_prevContext))
        std::cerr << "Failed to switch from pbuffer rendering" << std::endl;
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::initialiseTexture()
{
    // save old texture binding
    GLuint old_tex;
    glGetIntegerv(GL_TEXTURE_BINDING_2D, reinterpret_cast<GLint*>(&old_tex));

    // create and setup texture which pbuffer content will be loaded to
    glGenTextures(1, &d_texture);
    glBindTexture(GL_TEXTURE_2D, d_texture);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);

    // restore previous texture binding.
    glBindTexture(GL_TEXTURE_2D, old_tex);
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::selectFBConfig()
{
    int cfgcnt;
    GLXFBConfig* glxcfgs;

    glxcfgs = glXChooseFBConfig(d_dpy, DefaultScreen(d_dpy), pbAttrs, &cfgcnt);
    if (!glxcfgs)
        CEGUI_THROW(RendererException(
            "OpenGLGLXPBTextureTarget::selectFBConfig - pbuffer creation "
            "failure, can't get suitable configuration."));

    d_fbconfig = glxcfgs[0];
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::createContext()
{
    d_context = glXCreateNewContext(d_dpy, d_fbconfig, GLX_RGBA_TYPE,
                                    glXGetCurrentContext(), true);

    if (!d_context)
        CEGUI_THROW(RendererException(
            "OpenGLGLXPBTextureTarget::createContext - "
            "Failed to create GLX context for pbuffer."));
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::grabTexture()
{
    if (d_pbuffer)
    {
        glXDestroyPbuffer(d_dpy, d_pbuffer);
        d_pbuffer = 0;
    }

    OpenGLTextureTarget::grabTexture();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::restoreTexture()
{
    OpenGLTextureTarget::restoreTexture();
    initialiseTexture();
    initialisePBuffer();
}

//----------------------------------------------------------------------------//

} // End of  CEGUI namespace section
<commit_msg>FIX: Blend mode issue in OpenGL renderer when using GLX pbuffer based targets.<commit_after>/***********************************************************************
    filename:   CEGUIOpenGLGLXPBTextureTarget.cpp
    created:    Sat Jan 31 2009
    author:     Paul D Turner
*************************************************************************/
/***************************************************************************
 *   Copyright (C) 2004 - 2009 Paul D Turner & The CEGUI Development Team
 *
 *   Permission is hereby granted, free of charge, to any person obtaining
 *   a copy of this software and associated documentation files (the
 *   "Software"), to deal in the Software without restriction, including
 *   without limitation the rights to use, copy, modify, merge, publish,
 *   distribute, sublicense, and/or sell copies of the Software, and to
 *   permit persons to whom the Software is furnished to do so, subject to
 *   the following conditions:
 *
 *   The above copyright notice and this permission notice shall be
 *   included in all copies or substantial portions of the Software.
 *
 *   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 *   EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 *   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
 *   IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
 *   OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
 *   ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 *   OTHER DEALINGS IN THE SOFTWARE.
 ***************************************************************************/
#include "CEGUIOpenGLGLXPBTextureTarget.h"
#include "CEGUIExceptions.h"
#include "CEGUIRenderQueue.h"
#include "CEGUIGeometryBuffer.h"

#include "CEGUIOpenGLRenderer.h"
#include "CEGUIOpenGLTexture.h"

#include <iostream>

// Start of CEGUI namespace section
namespace CEGUI
{
//----------------------------------------------------------------------------//
const float OpenGLGLXPBTextureTarget::DEFAULT_SIZE = 128.0f;

//----------------------------------------------------------------------------//
// internal attribute array used to get pbuffer configs
int pbAttrs[] =
{
    GLX_DRAWABLE_TYPE, GLX_PBUFFER_BIT,
    GLX_DOUBLEBUFFER, GL_FALSE,
    GLX_RED_SIZE, 8,
    GLX_GREEN_SIZE, 8,
    GLX_BLUE_SIZE, 8,
    GLX_ALPHA_SIZE, 8,
    None
};

//----------------------------------------------------------------------------//
OpenGLGLXPBTextureTarget::OpenGLGLXPBTextureTarget(OpenGLRenderer& owner) :
    OpenGLTextureTarget(owner),
    d_pbuffer(0)
{
    if (!GLXEW_VERSION_1_3)
        CEGUI_THROW(InvalidRequestException("System does not support GLX >= 1.3 "
            "required by CEGUI pbuffer usage under GLX"));

    d_dpy = glXGetCurrentDisplay();

    selectFBConfig();
    createContext();
    initialiseTexture();

    // set default size (and cause initialisation of the pbuffer)
    declareRenderSize(Size(DEFAULT_SIZE, DEFAULT_SIZE));

    // set some states as a one-time thing (because we use a separate context)
    enablePBuffer();

    glEnable(GL_SCISSOR_TEST);
    glEnable(GL_TEXTURE_2D);
    glEnable(GL_BLEND);
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_COLOR_ARRAY);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
    glDisableClientState(GL_SECONDARY_COLOR_ARRAY);
    glDisableClientState(GL_INDEX_ARRAY);
    glDisableClientState(GL_NORMAL_ARRAY);
    glDisableClientState(GL_FOG_COORDINATE_ARRAY);
    glDisableClientState(GL_EDGE_FLAG_ARRAY);
    glClearColor(0,0,0,0);

    disablePBuffer();
}

//----------------------------------------------------------------------------//
OpenGLGLXPBTextureTarget::~OpenGLGLXPBTextureTarget()
{
    if (d_pbuffer)
        glXDestroyPbuffer(d_dpy, d_pbuffer);
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::activate()
{
    enablePBuffer();

    // we clear the blend mode here so the next setupRenderingBlendMode call
    // is forced to update states for our local context.
    d_owner.setupRenderingBlendMode(BM_INVALID);

    OpenGLRenderTarget::activate();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::deactivate()
{
    // grab what we rendered into the texture
    glBindTexture(GL_TEXTURE_2D, d_texture);
    glCopyTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8,
                     0, 0,
                     static_cast<GLsizei>(d_area.d_right),
                     static_cast<GLsizei>(d_area.d_bottom), 0);

    disablePBuffer();

    // Clear the blend mode again so the next setupRenderingBlendMode call
    // is forced to update states for the main / previous context.
    d_owner.setupRenderingBlendMode(BM_INVALID);

    OpenGLRenderTarget::deactivate();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::clear()
{
    enablePBuffer();
    glDisable(GL_SCISSOR_TEST);
    glClear(GL_COLOR_BUFFER_BIT);
    glEnable(GL_SCISSOR_TEST);
    disablePBuffer();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::declareRenderSize(const Size& sz)
{
    // exit if current size is enough
    if ((d_area.getWidth() >= sz.d_width) &&
        (d_area.getHeight() >= sz.d_height))
            return;

    setArea(Rect(d_area.getPosition(), d_owner.getAdjustedTextureSize(sz)));
    initialisePBuffer();
    clear();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::initialisePBuffer()
{
    int creation_attrs[] =
    {
        GLX_PBUFFER_WIDTH, d_area.getWidth(),
        GLX_PBUFFER_HEIGHT, d_area.getHeight(),
        GLX_LARGEST_PBUFFER, True,
        GLX_PRESERVED_CONTENTS, True,
        None
    };

    // release any existing pbuffer
    if (d_pbuffer)
        glXDestroyPbuffer(d_dpy, d_pbuffer);

    d_pbuffer = glXCreatePbuffer(d_dpy, d_fbconfig, creation_attrs);

    if (!d_pbuffer)
        CEGUI_THROW(RendererException(
            "OpenGLGLXPBTextureTarget::initialisePBuffer - "
            "pbuffer creation error:  glXCreatePbuffer() failed"));

    // get the real size of the buffer that was created
    GLuint actual_width, actual_height;
    glXQueryDrawable(d_dpy, d_pbuffer, GLX_WIDTH, &actual_width);
    glXQueryDrawable(d_dpy, d_pbuffer, GLX_HEIGHT, &actual_height);
    d_area.setSize(Size(actual_width, actual_height));

    // ensure CEGUI::Texture is wrapping real GL texture and has correct size
    d_CEGUITexture->setOpenGLTexture(d_texture, d_area.getSize());
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::enablePBuffer() const
{
    // switch to using the pbuffer
    d_prevDisplay = glXGetCurrentDisplay();
    d_prevDrawable = glXGetCurrentDrawable();
    d_prevContext = glXGetCurrentContext();

    if (!glXMakeCurrent(d_dpy, d_pbuffer, d_context))
        std::cerr << "Failed to switch to pbuffer for rendering" << std::endl;
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::disablePBuffer() const
{
    // switch back to rendering to previous set up
    if (!glXMakeCurrent(d_prevDisplay, d_prevDrawable, d_prevContext))
        std::cerr << "Failed to switch from pbuffer rendering" << std::endl;
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::initialiseTexture()
{
    // save old texture binding
    GLuint old_tex;
    glGetIntegerv(GL_TEXTURE_BINDING_2D, reinterpret_cast<GLint*>(&old_tex));

    // create and setup texture which pbuffer content will be loaded to
    glGenTextures(1, &d_texture);
    glBindTexture(GL_TEXTURE_2D, d_texture);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);

    // restore previous texture binding.
    glBindTexture(GL_TEXTURE_2D, old_tex);
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::selectFBConfig()
{
    int cfgcnt;
    GLXFBConfig* glxcfgs;

    glxcfgs = glXChooseFBConfig(d_dpy, DefaultScreen(d_dpy), pbAttrs, &cfgcnt);
    if (!glxcfgs)
        CEGUI_THROW(RendererException(
            "OpenGLGLXPBTextureTarget::selectFBConfig - pbuffer creation "
            "failure, can't get suitable configuration."));

    d_fbconfig = glxcfgs[0];
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::createContext()
{
    d_context = glXCreateNewContext(d_dpy, d_fbconfig, GLX_RGBA_TYPE,
                                    glXGetCurrentContext(), true);

    if (!d_context)
        CEGUI_THROW(RendererException(
            "OpenGLGLXPBTextureTarget::createContext - "
            "Failed to create GLX context for pbuffer."));
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::grabTexture()
{
    if (d_pbuffer)
    {
        glXDestroyPbuffer(d_dpy, d_pbuffer);
        d_pbuffer = 0;
    }

    OpenGLTextureTarget::grabTexture();
}

//----------------------------------------------------------------------------//
void OpenGLGLXPBTextureTarget::restoreTexture()
{
    OpenGLTextureTarget::restoreTexture();
    initialiseTexture();
    initialisePBuffer();
}

//----------------------------------------------------------------------------//

} // End of  CEGUI namespace section
<|endoftext|>


<commit_before>/*
 * Copyright(c) Sophist Solutions, Inc. 1990-2014.  All rights reserved
 */
#include    "Stroika/Frameworks/StroikaPreComp.h"

#include    <iostream>

#include    "Stroika/Foundation/Characters/Format.h"
#include    "Stroika/Foundation/DataExchange/JSON/Writer.h"
#include    "Stroika/Foundation/Execution/CommandLine.h"
#if     qPlatform_POSIX
#include    "Stroika/Foundation/Execution/SignalHandlers.h"
#endif
#include    "Stroika/Foundation/Execution/WaitableEvent.h"
#include    "Stroika/Foundation/Memory/Optional.h"
#include    "Stroika/Foundation/Streams/BasicBinaryOutputStream.h"

#include    "Stroika/Frameworks/SystemPerformance/AllInstruments.h"
#include    "Stroika/Frameworks/SystemPerformance/Capturer.h"
#include    "Stroika/Frameworks/SystemPerformance/Measurement.h"

using   namespace std;

using   namespace Stroika::Foundation;
using   namespace Stroika::Frameworks;
using   namespace Stroika::Frameworks::SystemPerformance;

using   Characters::Character;
using   Characters::String;
using   Containers::Sequence;
using   Memory::Optional;

namespace {
    string  Serialize_ (VariantValue v, bool oneLineMode)
    {
        Streams::BasicBinaryOutputStream    out;
        DataExchange::JSON::Writer ().Write (v, out);
        // strip CRLF - so shows up on one line
        String result = String::FromUTF8 (out.As<string> ());
        if (oneLineMode) {
            result = result.StripAll ([] (Character c)-> bool { return c == '\n' or c == '\r';});
        }
        return result.AsNarrowSDKString ();
    }
}

int main (int argc, const char* argv[])
{
#if     qPlatform_POSIX
    // Many performance instruments use pipes
    // @todo - REVIEW IF REALLY NEEDED AND WHY? SO LONG AS NO FAIL SHOULDNT BE?
    //  --LGP 2014-02-05
    Execution::SignalHandlerRegistry::Get ().SetSignalHandlers (SIGPIPE, Execution::SignalHandlerRegistry::kIGNORED);
#endif
    bool                        printUsage  =   false;
    bool                        printNames  =   false;
    bool                        oneLineMode =   false;
    Time::DurationSecondsType   runFor      =   30.0;
    Set<InstrumentNameType> run;
    Sequence<String>  args    =   Execution::ParseCommandLine (argc, argv);
    for (auto argi = args.begin (); argi != args.end(); ++argi) {
        if (Execution::MatchesCommandLineArgument (*argi, L"h")) {
            printUsage = true;
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"l")) {
            printNames = true;
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"o")) {
            oneLineMode = true;
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"r")) {
            ++argi;
            if (argi != args.end ()) {
                run.Add (*argi);
            }
            else {
                cerr << "Expected arg to -r" << endl;
                return EXIT_FAILURE;
            }
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"t")) {
            ++argi;
            if (argi != args.end ()) {
                runFor = Characters::String2Float<Time::DurationSecondsType> (*argi);
            }
            else {
                cerr << "Expected arg to -t" << endl;
                return EXIT_FAILURE;
            }
        }
    }
    if (printUsage) {
        cerr << "Usage: SystemPerformanceClient [-h] [-l] [-f] [-r RUN-INSTRUMENT]*" << endl;
        cerr << "    -h prints this help" << endl;
        cerr << "    -o prints instrument results (with newlines stripped)" << endl;
        cerr << "    -l prints only the instrument names" << endl;
        cerr << "    -r runs the given instrument (it can be repeated)" << endl;
        cerr << "    -t time to run for" << endl;
        return EXIT_SUCCESS;
    }

    try {
        if (printNames) {
            cout << "Instrument:" << endl;
            for (Instrument i : SystemPerformance::GetAllInstruments ()) {
                cout << "  " << i.fInstrumentName.GetPrintName ().AsNarrowSDKString () << endl;
                // print measurements too?
            }
            return EXIT_SUCCESS;
        }

#if 1
        Capturer capturer;
        {
            CaptureSet cs;
            cs.SetRunPeriod (Duration (15));
            for (Instrument i : SystemPerformance::GetAllInstruments ()) {
                if (not run.empty ()) {
                    if (not run.Contains (i.fInstrumentName)) {
                        continue;
                    }
                }
                cs.AddInstrument (i);
            }
            capturer.AddCaptureSet (cs);
        }
        capturer.AddMeasurementsCallback ([oneLineMode] (MeasurementSet ms) {
            cout << "    Measured-At: " << ms.fMeasuredAt.Format ().AsNarrowSDKString () << endl;
            for (Measurement mi : ms.fMeasurements) {
                cout << "    " << mi.fType.GetPrintName ().AsNarrowSDKString () << ": " << Serialize_ (mi.fValue, oneLineMode) << endl;
            }
        });

        // run til timeout and then fall out...
        IgnoreExceptionsForCall (Execution::WaitableEvent ().Wait (runFor));
#else
        cout << "Results for each instrument:" << endl;
        for (Instrument i : SystemPerformance::GetAllInstruments ()) {
            if (not run.empty ()) {
                if (not run.Contains (i.fInstrumentName)) {
                    continue;
                }
            }
            cout << "  " << i.fInstrumentName.GetPrintName ().AsNarrowSDKString () << endl;
            MeasurementSet m = i.Capture ();
            if (m.fMeasurements.empty ()) {
                cout << "    NO DATA";
            }
            else {
                cout << "    Measured-At: " << m.fMeasuredAt.Format ().AsNarrowSDKString () << endl;
                for (Measurement mi : m.fMeasurements) {
                    cout << "    " << mi.fType.GetPrintName ().AsNarrowSDKString () << ": " << Serialize_ (mi.fValue, oneLineMode) << endl;
                }
            }
        }
#endif
    }
    catch (...) {
        cerr << "Exception - terminating..." << endl;
        return EXIT_FAILURE;
    }

    return EXIT_SUCCESS;
}
<commit_msg>Updated SamplePerformacneClient so had demo with and without Capturer module<commit_after>/*
 * Copyright(c) Sophist Solutions, Inc. 1990-2014.  All rights reserved
 */
#include    "Stroika/Frameworks/StroikaPreComp.h"

#include    <iostream>

#include    "Stroika/Foundation/Characters/Format.h"
#include    "Stroika/Foundation/DataExchange/JSON/Writer.h"
#include    "Stroika/Foundation/Execution/CommandLine.h"
#if     qPlatform_POSIX
#include    "Stroika/Foundation/Execution/SignalHandlers.h"
#endif
#include    "Stroika/Foundation/Execution/WaitableEvent.h"
#include    "Stroika/Foundation/Memory/Optional.h"
#include    "Stroika/Foundation/Streams/BasicBinaryOutputStream.h"

#include    "Stroika/Frameworks/SystemPerformance/AllInstruments.h"
#include    "Stroika/Frameworks/SystemPerformance/Capturer.h"
#include    "Stroika/Frameworks/SystemPerformance/Measurement.h"

using   namespace std;

using   namespace Stroika::Foundation;
using   namespace Stroika::Frameworks;
using   namespace Stroika::Frameworks::SystemPerformance;

using   Characters::Character;
using   Characters::String;
using   Containers::Sequence;
using   Memory::Optional;

namespace {
    string  Serialize_ (VariantValue v, bool oneLineMode)
    {
        Streams::BasicBinaryOutputStream    out;
        DataExchange::JSON::Writer ().Write (v, out);
        // strip CRLF - so shows up on one line
        String result = String::FromUTF8 (out.As<string> ());
        if (oneLineMode) {
            result = result.StripAll ([] (Character c)-> bool { return c == '\n' or c == '\r';});
        }
        return result.AsNarrowSDKString ();
    }
}

int main (int argc, const char* argv[])
{
#if     qPlatform_POSIX
    // Many performance instruments use pipes
    // @todo - REVIEW IF REALLY NEEDED AND WHY? SO LONG AS NO FAIL SHOULDNT BE?
    //  --LGP 2014-02-05
    Execution::SignalHandlerRegistry::Get ().SetSignalHandlers (SIGPIPE, Execution::SignalHandlerRegistry::kIGNORED);
#endif
    bool                        printUsage  =   false;
    bool                        printNames  =   false;
    bool                        oneLineMode =   false;
    Time::DurationSecondsType   runFor      =   30.0;
    Set<InstrumentNameType> run;
    Sequence<String>  args    =   Execution::ParseCommandLine (argc, argv);
    for (auto argi = args.begin (); argi != args.end(); ++argi) {
        if (Execution::MatchesCommandLineArgument (*argi, L"h")) {
            printUsage = true;
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"l")) {
            printNames = true;
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"o")) {
            oneLineMode = true;
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"r")) {
            ++argi;
            if (argi != args.end ()) {
                run.Add (*argi);
            }
            else {
                cerr << "Expected arg to -r" << endl;
                return EXIT_FAILURE;
            }
        }
        if (Execution::MatchesCommandLineArgument (*argi, L"t")) {
            ++argi;
            if (argi != args.end ()) {
                runFor = Characters::String2Float<Time::DurationSecondsType> (*argi);
            }
            else {
                cerr << "Expected arg to -t" << endl;
                return EXIT_FAILURE;
            }
        }
    }
    if (printUsage) {
        cerr << "Usage: SystemPerformanceClient [-h] [-l] [-f] [-r RUN-INSTRUMENT]*" << endl;
        cerr << "    -h prints this help" << endl;
        cerr << "    -o prints instrument results (with newlines stripped)" << endl;
        cerr << "    -l prints only the instrument names" << endl;
        cerr << "    -r runs the given instrument (it can be repeated)" << endl;
        cerr << "    -t time to run for" << endl;
        return EXIT_SUCCESS;
    }

    try {
        if (printNames) {
            cout << "Instrument:" << endl;
            for (Instrument i : SystemPerformance::GetAllInstruments ()) {
                cout << "  " << i.fInstrumentName.GetPrintName ().AsNarrowSDKString () << endl;
                // print measurements too?
            }
            return EXIT_SUCCESS;
        }

        bool    useCapturer =   runFor > 0;
        if (useCapturer) {
            /*
             * Demo using capturer
             */
            Capturer capturer;
            {
                CaptureSet cs;
                cs.SetRunPeriod (Duration (15));
                for (Instrument i : SystemPerformance::GetAllInstruments ()) {
                    if (not run.empty ()) {
                        if (not run.Contains (i.fInstrumentName)) {
                            continue;
                        }
                    }
                    cs.AddInstrument (i);
                }
                capturer.AddCaptureSet (cs);
            }
            capturer.AddMeasurementsCallback ([oneLineMode] (MeasurementSet ms) {
                cout << "    Measured-At: " << ms.fMeasuredAt.Format ().AsNarrowSDKString () << endl;
                for (Measurement mi : ms.fMeasurements) {
                    cout << "    " << mi.fType.GetPrintName ().AsNarrowSDKString () << ": " << Serialize_ (mi.fValue, oneLineMode) << endl;
                }
            });

            // run til timeout and then fall out...
            IgnoreExceptionsForCall (Execution::WaitableEvent ().Wait (runFor));
        }
        else {
            /*
             * Demo NOT using capturer
             */
            cout << "Results for each instrument:" << endl;
            for (Instrument i : SystemPerformance::GetAllInstruments ()) {
                if (not run.empty ()) {
                    if (not run.Contains (i.fInstrumentName)) {
                        continue;
                    }
                }
                cout << "  " << i.fInstrumentName.GetPrintName ().AsNarrowSDKString () << endl;
                MeasurementSet m = i.Capture ();
                if (m.fMeasurements.empty ()) {
                    cout << "    NO DATA";
                }
                else {
                    cout << "    Measured-At: " << m.fMeasuredAt.Format ().AsNarrowSDKString () << endl;
                    for (Measurement mi : m.fMeasurements) {
                        cout << "    " << mi.fType.GetPrintName ().AsNarrowSDKString () << ": " << Serialize_ (mi.fValue, oneLineMode) << endl;
                    }
                }
            }
        }
    }
    catch (...) {
        cerr << "Exception - terminating..." << endl;
        return EXIT_FAILURE;
    }

    return EXIT_SUCCESS;
}
<|endoftext|>


<commit_before>/*
 * Copyright 2013 The Chromium Authors. All rights reserved.
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */
#include "chrome/browser/chromeos/extensions/virtual_keyboard_browsertest.h"

#include <vector>

#include "ash/shell.h"
#include "base/command_line.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/render_widget_host_iterator.h"
#include "content/public/browser/site_instance.h"
#include "content/public/browser/web_contents.h"
#include "content/public/test/browser_test_utils.h"
#include "extensions/common/extension.h"
#include "ui/aura/client/aura_constants.h"
#include "ui/base/ime/input_method.h"
#include "ui/keyboard/keyboard_controller.h"
#include "ui/keyboard/keyboard_switches.h"

namespace {
const base::FilePath::CharType kWebuiTestDir[] = FILE_PATH_LITERAL("webui");

const base::FilePath::CharType kMockController[] =
    FILE_PATH_LITERAL("mock_controller.js");

const base::FilePath::CharType kMockTimer[] =
    FILE_PATH_LITERAL("mock_timer.js");

const char kVirtualKeyboardTestDir[] = "chromeos/virtual_keyboard";

const char kBaseKeyboardTestFramework[] = "virtual_keyboard_test_base.js";

const char kExtensionId[] = "mppnpdlheglhdfmldimlhpnegondlapf";

const char kVirtualKeyboardURL[] = "chrome://keyboard";

}  // namespace

VirtualKeyboardBrowserTestConfig::VirtualKeyboardBrowserTestConfig()
    : base_framework_(kBaseKeyboardTestFramework),
      extension_id_(kExtensionId),
      test_dir_(kVirtualKeyboardTestDir),
      url_(kVirtualKeyboardURL) {
}

VirtualKeyboardBrowserTestConfig::~VirtualKeyboardBrowserTestConfig() {};

void VirtualKeyboardBrowserTest::SetUpCommandLine(CommandLine* command_line) {
  command_line->AppendSwitch(keyboard::switches::kEnableVirtualKeyboard);
}

void VirtualKeyboardBrowserTest::RunTest(
    const base::FilePath& file,
    const VirtualKeyboardBrowserTestConfig& config) {
  ui_test_utils::NavigateToURL(browser(), GURL(config.url_));
  content::WebContents* web_contents =
      browser()->tab_strip_model()->GetActiveWebContents();
  content::WaitForLoadStop(web_contents);
  ASSERT_TRUE(web_contents);

  // Inject testing scripts.
  InjectJavascript(base::FilePath(kWebuiTestDir),
                   base::FilePath(kMockController));
  InjectJavascript(base::FilePath(kWebuiTestDir), base::FilePath(kMockTimer));
  InjectJavascript(base::FilePath(FILE_PATH_LITERAL(config.test_dir_)),
                   base::FilePath(FILE_PATH_LITERAL(config.base_framework_)));
  InjectJavascript(base::FilePath(FILE_PATH_LITERAL(config.test_dir_)), file);

  ASSERT_TRUE(content::ExecuteScript(web_contents, utf8_content_));

  // Inject DOM-automation test harness and run tests.
  std::vector<int> resource_ids;
  EXPECT_TRUE(ExecuteWebUIResourceTest(web_contents, resource_ids));
}

void VirtualKeyboardBrowserTest::ShowVirtualKeyboard() {
  aura::Window* window = ash::Shell::GetPrimaryRootWindow();
  ui::InputMethod* input_method =
      window->GetProperty(aura::client::kRootWindowInputMethodKey);
  ASSERT_TRUE(input_method);
  input_method->ShowImeIfNeeded();
}

content::RenderViewHost* VirtualKeyboardBrowserTest::GetKeyboardRenderViewHost(
    const std::string& id) {
  ShowVirtualKeyboard();
  GURL url = extensions::Extension::GetBaseURLFromExtensionId(id);
  scoped_ptr<content::RenderWidgetHostIterator> widgets(
      content::RenderWidgetHost::GetRenderWidgetHosts());
  while (content::RenderWidgetHost* widget = widgets->GetNextHost()) {
    if (widget->IsRenderView()) {
      content::RenderViewHost* view = content::RenderViewHost::From(widget);
      if (url == view->GetSiteInstance()->GetSiteURL()) {
        content::WebContents* wc =
            content::WebContents::FromRenderViewHost(view);
        // Waits for Polymer to load.
        content::WaitForLoadStop(wc);
        return view;
      }
    }
  }
  LOG(ERROR) << "Extension not found:" << url;
  return NULL;
}

void VirtualKeyboardBrowserTest::InjectJavascript(const base::FilePath& dir,
                                                  const base::FilePath& file) {
  base::FilePath path = ui_test_utils::GetTestFilePath(dir, file);
  std::string library_content;
  ASSERT_TRUE(base::ReadFileToString(path, &library_content)) << path.value();
  utf8_content_.append(library_content);
  utf8_content_.append(";\n");
}

// crbug.com/367817. Either this feature or just the test are depending
// on the presense of Object.observe which is presently disabled by default.
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_AttributesTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("attributes_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

// crbug.com/387372. This test started failing at Blink r176582.
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_TypingTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("typing_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, ControlKeysTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("control_keys_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, HideKeyboardKeyTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("hide_keyboard_key_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, KeysetTransitionTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("keyset_transition_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

// Fails when enabling Object.observe. See http://crbug.com/370004
#if defined(OS_CHROMEOS)
#define MAYBE_IsKeyboardLoaded DISABLED_IsKeyboardLoaded
#else
#define MAYBE_IsKeyboardLoaded IsKeyboardLoaded
#endif
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, MAYBE_IsKeyboardLoaded) {
  content::RenderViewHost* keyboard_rvh =
      GetKeyboardRenderViewHost(kExtensionId);
  ASSERT_TRUE(keyboard_rvh);
  bool loaded = false;
  std::string script = "!!chrome.virtualKeyboardPrivate";
  EXPECT_TRUE(content::ExecuteScriptAndExtractBool(
      keyboard_rvh,
      "window.domAutomationController.send(" + script + ");",
      &loaded));
  // Catches the regression in crbug.com/308653.
  ASSERT_TRUE(loaded);
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_EndToEndTest) {
  // Get the virtual keyboard's render view host.
  content::RenderViewHost* keyboard_rvh =
      GetKeyboardRenderViewHost(kExtensionId);
  ASSERT_TRUE(keyboard_rvh);

  // Get the test page's render view host.
  content::RenderViewHost* browser_rvh = browser()->tab_strip_model()->
      GetActiveWebContents()->GetRenderViewHost();
  ASSERT_TRUE(browser_rvh);

  // Set up the test page.
  GURL url = ui_test_utils::GetTestUrl(
      base::FilePath(),
      base::FilePath(FILE_PATH_LITERAL(
          "chromeos/virtual_keyboard/end_to_end_test.html")));
  ui_test_utils::NavigateToURL(browser(), url);

  // Press 'a' on keyboard.
  base::FilePath path = ui_test_utils::GetTestFilePath(
      base::FilePath(FILE_PATH_LITERAL(kVirtualKeyboardTestDir)),
      base::FilePath(FILE_PATH_LITERAL("end_to_end_test.js")));
  std::string script;
  ASSERT_TRUE(base::ReadFileToString(path, &script));
  EXPECT_TRUE(content::ExecuteScript(keyboard_rvh, script));
  // Verify 'a' appeared on test page.
  bool success = false;
  EXPECT_TRUE(content::ExecuteScriptAndExtractBool(
      browser_rvh,
      "success ? verifyInput('a') : waitForInput('a');",
      &success));
  ASSERT_TRUE(success);
}

// TODO(kevers|rsadam|bshe):  Add UI tests for remaining virtual keyboard
// functionality.
<commit_msg>Disable failing VirtualKeyboardBrowserTest.ControlKeysTest.<commit_after>/*
 * Copyright 2013 The Chromium Authors. All rights reserved.
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */
#include "chrome/browser/chromeos/extensions/virtual_keyboard_browsertest.h"

#include <vector>

#include "ash/shell.h"
#include "base/command_line.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/render_widget_host_iterator.h"
#include "content/public/browser/site_instance.h"
#include "content/public/browser/web_contents.h"
#include "content/public/test/browser_test_utils.h"
#include "extensions/common/extension.h"
#include "ui/aura/client/aura_constants.h"
#include "ui/base/ime/input_method.h"
#include "ui/keyboard/keyboard_controller.h"
#include "ui/keyboard/keyboard_switches.h"

namespace {
const base::FilePath::CharType kWebuiTestDir[] = FILE_PATH_LITERAL("webui");

const base::FilePath::CharType kMockController[] =
    FILE_PATH_LITERAL("mock_controller.js");

const base::FilePath::CharType kMockTimer[] =
    FILE_PATH_LITERAL("mock_timer.js");

const char kVirtualKeyboardTestDir[] = "chromeos/virtual_keyboard";

const char kBaseKeyboardTestFramework[] = "virtual_keyboard_test_base.js";

const char kExtensionId[] = "mppnpdlheglhdfmldimlhpnegondlapf";

const char kVirtualKeyboardURL[] = "chrome://keyboard";

}  // namespace

VirtualKeyboardBrowserTestConfig::VirtualKeyboardBrowserTestConfig()
    : base_framework_(kBaseKeyboardTestFramework),
      extension_id_(kExtensionId),
      test_dir_(kVirtualKeyboardTestDir),
      url_(kVirtualKeyboardURL) {
}

VirtualKeyboardBrowserTestConfig::~VirtualKeyboardBrowserTestConfig() {};

void VirtualKeyboardBrowserTest::SetUpCommandLine(CommandLine* command_line) {
  command_line->AppendSwitch(keyboard::switches::kEnableVirtualKeyboard);
}

void VirtualKeyboardBrowserTest::RunTest(
    const base::FilePath& file,
    const VirtualKeyboardBrowserTestConfig& config) {
  ui_test_utils::NavigateToURL(browser(), GURL(config.url_));
  content::WebContents* web_contents =
      browser()->tab_strip_model()->GetActiveWebContents();
  content::WaitForLoadStop(web_contents);
  ASSERT_TRUE(web_contents);

  // Inject testing scripts.
  InjectJavascript(base::FilePath(kWebuiTestDir),
                   base::FilePath(kMockController));
  InjectJavascript(base::FilePath(kWebuiTestDir), base::FilePath(kMockTimer));
  InjectJavascript(base::FilePath(FILE_PATH_LITERAL(config.test_dir_)),
                   base::FilePath(FILE_PATH_LITERAL(config.base_framework_)));
  InjectJavascript(base::FilePath(FILE_PATH_LITERAL(config.test_dir_)), file);

  ASSERT_TRUE(content::ExecuteScript(web_contents, utf8_content_));

  // Inject DOM-automation test harness and run tests.
  std::vector<int> resource_ids;
  EXPECT_TRUE(ExecuteWebUIResourceTest(web_contents, resource_ids));
}

void VirtualKeyboardBrowserTest::ShowVirtualKeyboard() {
  aura::Window* window = ash::Shell::GetPrimaryRootWindow();
  ui::InputMethod* input_method =
      window->GetProperty(aura::client::kRootWindowInputMethodKey);
  ASSERT_TRUE(input_method);
  input_method->ShowImeIfNeeded();
}

content::RenderViewHost* VirtualKeyboardBrowserTest::GetKeyboardRenderViewHost(
    const std::string& id) {
  ShowVirtualKeyboard();
  GURL url = extensions::Extension::GetBaseURLFromExtensionId(id);
  scoped_ptr<content::RenderWidgetHostIterator> widgets(
      content::RenderWidgetHost::GetRenderWidgetHosts());
  while (content::RenderWidgetHost* widget = widgets->GetNextHost()) {
    if (widget->IsRenderView()) {
      content::RenderViewHost* view = content::RenderViewHost::From(widget);
      if (url == view->GetSiteInstance()->GetSiteURL()) {
        content::WebContents* wc =
            content::WebContents::FromRenderViewHost(view);
        // Waits for Polymer to load.
        content::WaitForLoadStop(wc);
        return view;
      }
    }
  }
  LOG(ERROR) << "Extension not found:" << url;
  return NULL;
}

void VirtualKeyboardBrowserTest::InjectJavascript(const base::FilePath& dir,
                                                  const base::FilePath& file) {
  base::FilePath path = ui_test_utils::GetTestFilePath(dir, file);
  std::string library_content;
  ASSERT_TRUE(base::ReadFileToString(path, &library_content)) << path.value();
  utf8_content_.append(library_content);
  utf8_content_.append(";\n");
}

// crbug.com/367817. Either this feature or just the test are depending
// on the presense of Object.observe which is presently disabled by default.
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_AttributesTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("attributes_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

// crbug.com/387372. This test started failing at Blink r176582.
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_TypingTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("typing_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

// crbug.com/387372. This test started failing at Blink r176582.
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_ControlKeysTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("control_keys_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, HideKeyboardKeyTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("hide_keyboard_key_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, KeysetTransitionTest) {
  RunTest(base::FilePath(FILE_PATH_LITERAL("keyset_transition_test.js")),
          VirtualKeyboardBrowserTestConfig());
}

// Fails when enabling Object.observe. See http://crbug.com/370004
#if defined(OS_CHROMEOS)
#define MAYBE_IsKeyboardLoaded DISABLED_IsKeyboardLoaded
#else
#define MAYBE_IsKeyboardLoaded IsKeyboardLoaded
#endif
IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, MAYBE_IsKeyboardLoaded) {
  content::RenderViewHost* keyboard_rvh =
      GetKeyboardRenderViewHost(kExtensionId);
  ASSERT_TRUE(keyboard_rvh);
  bool loaded = false;
  std::string script = "!!chrome.virtualKeyboardPrivate";
  EXPECT_TRUE(content::ExecuteScriptAndExtractBool(
      keyboard_rvh,
      "window.domAutomationController.send(" + script + ");",
      &loaded));
  // Catches the regression in crbug.com/308653.
  ASSERT_TRUE(loaded);
}

IN_PROC_BROWSER_TEST_F(VirtualKeyboardBrowserTest, DISABLED_EndToEndTest) {
  // Get the virtual keyboard's render view host.
  content::RenderViewHost* keyboard_rvh =
      GetKeyboardRenderViewHost(kExtensionId);
  ASSERT_TRUE(keyboard_rvh);

  // Get the test page's render view host.
  content::RenderViewHost* browser_rvh = browser()->tab_strip_model()->
      GetActiveWebContents()->GetRenderViewHost();
  ASSERT_TRUE(browser_rvh);

  // Set up the test page.
  GURL url = ui_test_utils::GetTestUrl(
      base::FilePath(),
      base::FilePath(FILE_PATH_LITERAL(
          "chromeos/virtual_keyboard/end_to_end_test.html")));
  ui_test_utils::NavigateToURL(browser(), url);

  // Press 'a' on keyboard.
  base::FilePath path = ui_test_utils::GetTestFilePath(
      base::FilePath(FILE_PATH_LITERAL(kVirtualKeyboardTestDir)),
      base::FilePath(FILE_PATH_LITERAL("end_to_end_test.js")));
  std::string script;
  ASSERT_TRUE(base::ReadFileToString(path, &script));
  EXPECT_TRUE(content::ExecuteScript(keyboard_rvh, script));
  // Verify 'a' appeared on test page.
  bool success = false;
  EXPECT_TRUE(content::ExecuteScriptAndExtractBool(
      browser_rvh,
      "success ? verifyInput('a') : waitForInput('a');",
      &success));
  ASSERT_TRUE(success);
}

// TODO(kevers|rsadam|bshe):  Add UI tests for remaining virtual keyboard
// functionality.
<|endoftext|>


<commit_before>#include <QObject>
#include <QGraphicsSceneMouseEvent>

#include "dcpappletplugin.h"

#include "ut_dcpappletplugin.h"
#include "dcpappletplugin_p.h"
#include "qpluginloader-fake.h"
#include "dcpappletmetadata-fake.h"

void Ut_DcpAppletPlugin::init()
{
}

void Ut_DcpAppletPlugin::cleanup()
{
    delete m_subject;
    m_subject = 0;
}

void Ut_DcpAppletPlugin::initTestCase()
{
}

void Ut_DcpAppletPlugin::cleanupTestCase()
{
}

/**
 * checks if appletloader calls applet's init function
 */
void Ut_DcpAppletPlugin::testLoadBinaryOk()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_BINARY;
    qPluginLoaderFakeSuccessful = true;
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(m_subject->applet());
    QVERIFY(
        dynamic_cast<DcpAppletPluginApplet*>(m_subject->applet())->initialized()
        );
    delete metadata;
    QVERIFY(m_subject->isAppletLoaded());
}

/**
 * checks if appletloader returns 0 on load error and
 * errorMsg() contains the load error message coming from the QPluginLoader
 */
void Ut_DcpAppletPlugin::testLoadBinaryError()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_BINARY;
    qPluginLoaderFakeSuccessful = false;
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(!m_subject->applet());
    QVERIFY(m_subject->errorMsg().contains(fakeErrorMsg));
    QVERIFY(!m_subject->isAppletLoaded());
    delete metadata;
}

/**
 * TODO
 */
void Ut_DcpAppletPlugin::testLoadDsl()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_DSL;
    QSKIP("TODO: test DSL loading", SkipAll);
}

/**
 * checks if metadata() returns the same pointer that was given in
 * initialization
 */
void Ut_DcpAppletPlugin::testMetadata()
{
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(m_subject->metadata() == metadata);
    delete metadata;
}

void Ut_DcpAppletPlugin::testInterfaceVersion()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_BINARY;
    qPluginLoaderFakeSuccessful = true;
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(m_subject->applet());
    QCOMPARE(m_subject->interfaceVersion(), 2);
    delete m_subject->d_ptr->appletInstance;
    m_subject->d_ptr->appletInstance = 0;
    QCOMPARE(m_subject->interfaceVersion(), -1);
    delete metadata;
}

QTEST_APPLESS_MAIN(Ut_DcpAppletPlugin)
<commit_msg>fixing interface version in ut_dcpappletplugin<commit_after>#include <QObject>
#include <QGraphicsSceneMouseEvent>

#include "dcpappletplugin.h"

#include "ut_dcpappletplugin.h"
#include "dcpappletplugin_p.h"
#include "qpluginloader-fake.h"
#include "dcpappletmetadata-fake.h"

void Ut_DcpAppletPlugin::init()
{
}

void Ut_DcpAppletPlugin::cleanup()
{
    delete m_subject;
    m_subject = 0;
}

void Ut_DcpAppletPlugin::initTestCase()
{
}

void Ut_DcpAppletPlugin::cleanupTestCase()
{
}

/**
 * checks if appletloader calls applet's init function
 */
void Ut_DcpAppletPlugin::testLoadBinaryOk()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_BINARY;
    qPluginLoaderFakeSuccessful = true;
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(m_subject->applet());
    QVERIFY(
        dynamic_cast<DcpAppletPluginApplet*>(m_subject->applet())->initialized()
        );
    delete metadata;
    QVERIFY(m_subject->isAppletLoaded());
}

/**
 * checks if appletloader returns 0 on load error and
 * errorMsg() contains the load error message coming from the QPluginLoader
 */
void Ut_DcpAppletPlugin::testLoadBinaryError()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_BINARY;
    qPluginLoaderFakeSuccessful = false;
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(!m_subject->applet());
    QVERIFY(m_subject->errorMsg().contains(fakeErrorMsg));
    QVERIFY(!m_subject->isAppletLoaded());
    delete metadata;
}

/**
 * TODO
 */
void Ut_DcpAppletPlugin::testLoadDsl()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_DSL;
    QSKIP("TODO: test DSL loading", SkipAll);
}

/**
 * checks if metadata() returns the same pointer that was given in
 * initialization
 */
void Ut_DcpAppletPlugin::testMetadata()
{
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(m_subject->metadata() == metadata);
    delete metadata;
}

void Ut_DcpAppletPlugin::testInterfaceVersion()
{
    DcpAppletMetadataFake::appletType =
        DcpAppletMetadataFake::TYPE_BINARY;
    qPluginLoaderFakeSuccessful = true;
    DcpAppletMetadata *metadata = new DcpAppletMetadata("dummy-binary");
    m_subject = new DcpAppletPlugin(metadata);
    QVERIFY(m_subject->applet());
    QCOMPARE(m_subject->interfaceVersion(), 3);
    delete m_subject->d_ptr->appletInstance;
    m_subject->d_ptr->appletInstance = 0;
    QCOMPARE(m_subject->interfaceVersion(), -1);
    delete metadata;
}

QTEST_APPLESS_MAIN(Ut_DcpAppletPlugin)
<|endoftext|>


<commit_before>/*
 * Copyright(c) Sophist Solutions, Inc. 1990-2014.  All rights reserved
 */
#include    "../StroikaPreComp.h"

#include    <cstdarg>
#include    <cstdlib>
#include    <iomanip>
#include    <limits>
#include    <sstream>

#include    "../Containers/Common.h"
#include    "../Debug/Assertions.h"
#include    "../Debug/Trace.h"
#include    "../Math/Common.h"
#include    "../Memory/SmallStackBuffer.h"
#include    "CodePage.h"

#include    "Format.h"

using   namespace   Stroika::Foundation;
using   namespace   Stroika::Foundation::Characters;
using   namespace   Stroika::Foundation::Memory;

/*
 ********************************************************************************
 ************************************* Format ***********************************
 ********************************************************************************
 */
DISABLE_COMPILER_MSC_WARNING_START(6262)
String Characters::FormatV (const wchar_t* format, va_list argsList)
{
    RequireNotNull (format);
    Memory::SmallStackBuffer<wchar_t, 10 * 1024>  msgBuf (10 * 1024);
    const   wchar_t*    useFormat   =   format;
#if     !qStdLibSprintfAssumesPctSIsWideInFormatIfWideFormat
    wchar_t     newFormat[5 * 1024];
    {
        size_t  origFormatLen   =   wcslen (format);
        Require (origFormatLen < NEltsOf (newFormat) / 2);  // just to be sure safe - this is already crazy-big for format string...
        // Could use Memory::SmallStackBuffer<> but I doubt this will ever get triggered
        bool lookingAtFmtCvt = false;
        size_t  newFormatIdx    =   0;
        for (size_t i = 0; i < origFormatLen; ++i) {
            if (lookingAtFmtCvt) {
                switch (format[i]) {
                    case    '%': {
                            lookingAtFmtCvt = false;
                        }
                        break;
                    case    's': {
                            newFormat[newFormatIdx] = 'l';
                            newFormatIdx++;
                            lookingAtFmtCvt = false;    // DONE
                        }
                        break;
                    case    '.': {
                            // could still be part for format string
                        }
                        break;
                    default: {
                            if (isdigit (format[i])) {
                                // could still be part for format string
                            }
                            else {
                                lookingAtFmtCvt = false;    // DONE
                            }
                        }
                        break;
                }
            }
            else {
                if (format[i] == '%') {
                    lookingAtFmtCvt = true;
                }
            }
            newFormat[newFormatIdx] = format[i];
            newFormatIdx++;
        }
        Assert (newFormatIdx >= origFormatLen);
        if (newFormatIdx > origFormatLen) {
            newFormat[newFormatIdx] = '\0';
            useFormat   =   newFormat;
        }
    }
#endif

#if     qSupportValgrindQuirks
    // Makes little sense - even msgBuf[0] not sufficient - but this silences lots of warnings.
    // -- LGP 2012-05-19
    memset (msgBuf, 0, sizeof (msgBuf[0]) * msgBuf.GetSize());
#endif

    // Assume only reason for failure is not enuf bytes, so allocate more.
    // If I'm wrong, we'll just runout of memory and throw out...
    while (::vswprintf (msgBuf, msgBuf.GetSize (), useFormat, argsList) < 0) {
        msgBuf.GrowToSize (msgBuf.GetSize () * 2);
    }
    Assert (::wcslen (msgBuf) < msgBuf.GetSize ());
    return String (msgBuf);
}
DISABLE_COMPILER_MSC_WARNING_END(6262)

/*
********************************************************************************
************************************* Format ***********************************
********************************************************************************
*/
String Characters::Format (const wchar_t* format, ...)
{
    va_list     argsList;
    va_start (argsList, format);
    String tmp = FormatV (format, argsList);
    va_end (argsList);
    return move (tmp);
}

/*
 ********************************************************************************
 *************************** StripTrailingCharIfAny *****************************
 ********************************************************************************
 */
String Characters::StripTrailingCharIfAny (const String& s, wchar_t c)
{
    if (s.size () > 0 and s[s.size () - 1] == c) {
        String  tmp =   s;
        tmp.erase (tmp.size () - 1);
        return tmp;
    }
    return s;
}

<commit_msg>Cosmetic<commit_after>/*
 * Copyright(c) Sophist Solutions, Inc. 1990-2014.  All rights reserved
 */
#include    "../StroikaPreComp.h"

#include    <cstdarg>
#include    <cstdlib>
#include    <iomanip>
#include    <limits>
#include    <sstream>

#include    "../Containers/Common.h"
#include    "../Debug/Assertions.h"
#include    "../Debug/Trace.h"
#include    "../Math/Common.h"
#include    "../Memory/SmallStackBuffer.h"
#include    "CodePage.h"

#include    "Format.h"

using   namespace   Stroika::Foundation;
using   namespace   Stroika::Foundation::Characters;
using   namespace   Stroika::Foundation::Memory;

/*
 ********************************************************************************
 ************************************* Format ***********************************
 ********************************************************************************
 */
DISABLE_COMPILER_MSC_WARNING_START(6262)
String Characters::FormatV (const wchar_t* format, va_list argsList)
{
    RequireNotNull (format);
    Memory::SmallStackBuffer<wchar_t, 10 * 1024>  msgBuf (10 * 1024);
    const   wchar_t*    useFormat   =   format;
#if     !qStdLibSprintfAssumesPctSIsWideInFormatIfWideFormat
    wchar_t     newFormat[5 * 1024];
    {
        size_t  origFormatLen   =   wcslen (format);
        Require (origFormatLen < NEltsOf (newFormat) / 2);  // just to be sure safe - this is already crazy-big for format string...
        // Could use Memory::SmallStackBuffer<> but I doubt this will ever get triggered
        bool lookingAtFmtCvt = false;
        size_t  newFormatIdx    =   0;
        for (size_t i = 0; i < origFormatLen; ++i) {
            if (lookingAtFmtCvt) {
                switch (format[i]) {
                    case    '%': {
                            lookingAtFmtCvt = false;
                        }
                        break;
                    case    's': {
                            newFormat[newFormatIdx] = 'l';
                            newFormatIdx++;
                            lookingAtFmtCvt = false;    // DONE
                        }
                        break;
                    case    '.': {
                            // could still be part for format string
                        }
                        break;
                    default: {
                            if (isdigit (format[i])) {
                                // could still be part for format string
                            }
                            else {
                                lookingAtFmtCvt = false;    // DONE
                            }
                        }
                        break;
                }
            }
            else {
                if (format[i] == '%') {
                    lookingAtFmtCvt = true;
                }
            }
            newFormat[newFormatIdx] = format[i];
            newFormatIdx++;
        }
        Assert (newFormatIdx >= origFormatLen);
        if (newFormatIdx > origFormatLen) {
            newFormat[newFormatIdx] = '\0';
            useFormat   =   newFormat;
        }
    }
#endif

#if     qSupportValgrindQuirks
    // Makes little sense - even msgBuf[0] not sufficient - but this silences lots of warnings.
    // -- LGP 2012-05-19
    memset (msgBuf, 0, sizeof (msgBuf[0]) * msgBuf.GetSize());
#endif

    // Assume only reason for failure is not enuf bytes, so allocate more.
    // If I'm wrong, we'll just runout of memory and throw out...
    while (::vswprintf (msgBuf, msgBuf.GetSize (), useFormat, argsList) < 0) {
        msgBuf.GrowToSize (msgBuf.GetSize () * 2);
    }
    Assert (::wcslen (msgBuf) < msgBuf.GetSize ());
    return String (msgBuf);
}
DISABLE_COMPILER_MSC_WARNING_END(6262)

/*
********************************************************************************
************************************* Format ***********************************
********************************************************************************
*/
String Characters::Format (const wchar_t* format, ...)
{
    va_list     argsList;
    va_start (argsList, format);
    String tmp = FormatV (format, argsList);
    va_end (argsList);
    return move (tmp);
}

/*
 ********************************************************************************
 *************************** StripTrailingCharIfAny *****************************
 ********************************************************************************
 */
String	Characters::StripTrailingCharIfAny (const String& s, wchar_t c)
{
    if (s.size () > 0 and s[s.size () - 1] == c) {
        String  tmp =   s;
        tmp.erase (tmp.size () - 1);
        return tmp;
    }
    return s;
}

<|endoftext|>