<commit_before>#include "master.hpp"

namespace factor
{

void factor_vm::init_card_decks()
{
	cards_offset = (cell)data->cards - addr_to_card(data->start);
	decks_offset = (cell)data->decks - addr_to_deck(data->start);
}

data_heap::data_heap(cell young_size_,
	cell aging_size_,
	cell tenured_size_)
{
	young_size_ = align(young_size_,deck_size);
	aging_size_ = align(aging_size_,deck_size);
	tenured_size_ = align(tenured_size_,deck_size);

	young_size = young_size_;
	aging_size = aging_size_;
	tenured_size = tenured_size_;

	cell total_size = young_size + 2 * aging_size + tenured_size + deck_size;
	seg = new segment(total_size,false);

	cell cards_size = addr_to_card(total_size);
	cards = new card[cards_size];
	cards_end = cards + cards_size;
	memset(cards,0,cards_size);

	cell decks_size = addr_to_deck(total_size);
	decks = new card_deck[decks_size];
	decks_end = decks + decks_size;
	memset(decks,0,decks_size);

	start = align(seg->start,deck_size);

	tenured = new tenured_space(tenured_size,start);

	aging = new aging_space(aging_size,tenured->end);
	aging_semispace = new aging_space(aging_size,aging->end);

	nursery = new nursery_space(young_size,aging_semispace->end);

	assert(seg->end - nursery->end <= deck_size);
}

data_heap::~data_heap()
{
	delete seg;
	delete nursery;
	delete aging;
	delete aging_semispace;
	delete tenured;
	delete[] cards;
	delete[] decks;
}

data_heap *data_heap::grow(cell requested_bytes)
{
	cell new_tenured_size = (tenured_size * 2) + requested_bytes;
	return new data_heap(young_size,
		aging_size,
		new_tenured_size);
}

template<typename Generation> void data_heap::clear_cards(Generation *gen)
{
	cell first_card = addr_to_card(gen->start - start);
	cell last_card = addr_to_card(gen->end - start);
	memset(&cards[first_card],0,last_card - first_card);
}

template<typename Generation> void data_heap::clear_decks(Generation *gen)
{
	cell first_deck = addr_to_deck(gen->start - start);
	cell last_deck = addr_to_deck(gen->end - start);
	memset(&decks[first_deck],0,last_deck - first_deck);
}

void data_heap::reset_generation(nursery_space *gen)
{
	gen->here = gen->start;
}

void data_heap::reset_generation(aging_space *gen)
{
	gen->here = gen->start;
	clear_cards(gen);
	clear_decks(gen);
	gen->starts.clear_object_start_offsets();
}

void data_heap::reset_generation(tenured_space *gen)
{
	clear_cards(gen);
	clear_decks(gen);
}

bool data_heap::low_memory_p()
{
	return (tenured->free_space() <= nursery->size + aging->size);
}

void data_heap::mark_all_cards()
{
	memset(cards,-1,cards_end - cards);
	memset(decks,-1,decks_end - decks);
}

void factor_vm::set_data_heap(data_heap *data_)
{
	data = data_;
	nursery = *data->nursery;
	init_card_decks();
}

void factor_vm::init_data_heap(cell young_size, cell aging_size, cell tenured_size)
{
	set_data_heap(new data_heap(young_size,aging_size,tenured_size));
}

/* Size of the object pointed to by an untagged pointer */
cell object::size() const
{
	if(free_p()) return ((free_heap_block *)this)->size();

	switch(type())
	{
	case ARRAY_TYPE:
		return align(array_size((array*)this),data_alignment);
	case BIGNUM_TYPE:
		return align(array_size((bignum*)this),data_alignment);
	case BYTE_ARRAY_TYPE:
		return align(array_size((byte_array*)this),data_alignment);
	case STRING_TYPE:
		return align(string_size(string_capacity((string*)this)),data_alignment);
	case TUPLE_TYPE:
		{
			tuple_layout *layout = (tuple_layout *)UNTAG(((tuple *)this)->layout);
			return align(tuple_size(layout),data_alignment);
		}
	case QUOTATION_TYPE:
		return align(sizeof(quotation),data_alignment);
	case WORD_TYPE:
		return align(sizeof(word),data_alignment);
	case FLOAT_TYPE:
		return align(sizeof(boxed_float),data_alignment);
	case DLL_TYPE:
		return align(sizeof(dll),data_alignment);
	case ALIEN_TYPE:
		return align(sizeof(alien),data_alignment);
	case WRAPPER_TYPE:
		return align(sizeof(wrapper),data_alignment);
	case CALLSTACK_TYPE:
		return align(callstack_size(untag_fixnum(((callstack *)this)->length)),data_alignment);
	default:
		critical_error("Invalid header",(cell)this);
		return 0; /* can't happen */
	}
}

/* The number of cells from the start of the object which should be scanned by
the GC. Some types have a binary payload at the end (string, word, DLL) which
we ignore. */
cell object::binary_payload_start() const
{
	if(free_p()) return 0;

	switch(type())
	{
	/* these objects do not refer to other objects at all */
	case FLOAT_TYPE:
	case BYTE_ARRAY_TYPE:
	case BIGNUM_TYPE:
	case CALLSTACK_TYPE:
		return 0;
	/* these objects have some binary data at the end */
	case WORD_TYPE:
		return sizeof(word) - sizeof(cell) * 3;
	case ALIEN_TYPE:
		return sizeof(cell) * 3;
	case DLL_TYPE:
		return sizeof(cell) * 2;
	case QUOTATION_TYPE:
		return sizeof(quotation) - sizeof(cell) * 2;
	case STRING_TYPE:
		return sizeof(string);
	/* everything else consists entirely of pointers */
	case ARRAY_TYPE:
		return array_size<array>(array_capacity((array*)this));
	case TUPLE_TYPE:
		return tuple_size(untag<tuple_layout>(((tuple *)this)->layout));
	case WRAPPER_TYPE:
		return sizeof(wrapper);
	default:
		critical_error("Invalid header",(cell)this);
                return 0; /* can't happen */
	}
}

data_heap_room factor_vm::data_room()
{
	data_heap_room room;

	room.nursery_size             = nursery.size;
	room.nursery_occupied         = nursery.occupied_space();
	room.nursery_free             = nursery.free_space();
	room.aging_size               = data->aging->size;
	room.aging_occupied           = data->aging->occupied_space();
	room.aging_free               = data->aging->free_space();
	room.tenured_size             = data->tenured->size;
	room.tenured_occupied         = data->tenured->occupied_space();
	room.tenured_total_free       = data->tenured->free_space();
	room.tenured_contiguous_free  = data->tenured->largest_free_block();
	room.tenured_free_block_count = data->tenured->free_block_count();
	room.cards                    = data->cards_end - data->cards;
	room.decks                    = data->decks_end - data->decks;
	room.mark_stack               = mark_stack.capacity() * sizeof(cell);

	return room;
}

void factor_vm::primitive_data_room()
{
	data_heap_room room = data_room();
	dpush(tag<byte_array>(byte_array_from_value(&room)));
}

struct object_accumulator {
	cell type;
	std::vector<cell> objects;

	explicit object_accumulator(cell type_) : type(type_) {}

	void operator()(object *obj)
	{
		if(type == TYPE_COUNT || obj->type() == type)
			objects.push_back(tag_dynamic(obj));
	}
};

cell factor_vm::instances(cell type)
{
	object_accumulator accum(type);
	each_object(accum);
	cell object_count = accum.objects.size();

	data_roots.push_back(data_root_range(&accum.objects[0],object_count));

	array *objects = allot_array(object_count,false_object);
	memcpy(objects->data(),&accum.objects[0],object_count * sizeof(cell));

	data_roots.pop_back();

	return tag<array>(objects);
}

void factor_vm::primitive_all_instances()
{
	primitive_full_gc();
	dpush(instances(TYPE_COUNT));
}

cell factor_vm::find_all_words()
{
	return instances(WORD_TYPE);
}

}
<commit_msg>vm: be more eager to do a full collection to avoid fragmentation leading to heap growth<commit_after>#include "master.hpp"

namespace factor
{

void factor_vm::init_card_decks()
{
	cards_offset = (cell)data->cards - addr_to_card(data->start);
	decks_offset = (cell)data->decks - addr_to_deck(data->start);
}

data_heap::data_heap(cell young_size_,
	cell aging_size_,
	cell tenured_size_)
{
	young_size_ = align(young_size_,deck_size);
	aging_size_ = align(aging_size_,deck_size);
	tenured_size_ = align(tenured_size_,deck_size);

	young_size = young_size_;
	aging_size = aging_size_;
	tenured_size = tenured_size_;

	cell total_size = young_size + 2 * aging_size + tenured_size + deck_size;
	seg = new segment(total_size,false);

	cell cards_size = addr_to_card(total_size);
	cards = new card[cards_size];
	cards_end = cards + cards_size;
	memset(cards,0,cards_size);

	cell decks_size = addr_to_deck(total_size);
	decks = new card_deck[decks_size];
	decks_end = decks + decks_size;
	memset(decks,0,decks_size);

	start = align(seg->start,deck_size);

	tenured = new tenured_space(tenured_size,start);

	aging = new aging_space(aging_size,tenured->end);
	aging_semispace = new aging_space(aging_size,aging->end);

	nursery = new nursery_space(young_size,aging_semispace->end);

	assert(seg->end - nursery->end <= deck_size);
}

data_heap::~data_heap()
{
	delete seg;
	delete nursery;
	delete aging;
	delete aging_semispace;
	delete tenured;
	delete[] cards;
	delete[] decks;
}

data_heap *data_heap::grow(cell requested_bytes)
{
	cell new_tenured_size = (tenured_size * 2) + requested_bytes;
	return new data_heap(young_size,
		aging_size,
		new_tenured_size);
}

template<typename Generation> void data_heap::clear_cards(Generation *gen)
{
	cell first_card = addr_to_card(gen->start - start);
	cell last_card = addr_to_card(gen->end - start);
	memset(&cards[first_card],0,last_card - first_card);
}

template<typename Generation> void data_heap::clear_decks(Generation *gen)
{
	cell first_deck = addr_to_deck(gen->start - start);
	cell last_deck = addr_to_deck(gen->end - start);
	memset(&decks[first_deck],0,last_deck - first_deck);
}

void data_heap::reset_generation(nursery_space *gen)
{
	gen->here = gen->start;
}

void data_heap::reset_generation(aging_space *gen)
{
	gen->here = gen->start;
	clear_cards(gen);
	clear_decks(gen);
	gen->starts.clear_object_start_offsets();
}

void data_heap::reset_generation(tenured_space *gen)
{
	clear_cards(gen);
	clear_decks(gen);
}

bool data_heap::low_memory_p()
{
	return (tenured->largest_free_block() <= nursery->size + aging->size);
}

void data_heap::mark_all_cards()
{
	memset(cards,-1,cards_end - cards);
	memset(decks,-1,decks_end - decks);
}

void factor_vm::set_data_heap(data_heap *data_)
{
	data = data_;
	nursery = *data->nursery;
	init_card_decks();
}

void factor_vm::init_data_heap(cell young_size, cell aging_size, cell tenured_size)
{
	set_data_heap(new data_heap(young_size,aging_size,tenured_size));
}

/* Size of the object pointed to by an untagged pointer */
cell object::size() const
{
	if(free_p()) return ((free_heap_block *)this)->size();

	switch(type())
	{
	case ARRAY_TYPE:
		return align(array_size((array*)this),data_alignment);
	case BIGNUM_TYPE:
		return align(array_size((bignum*)this),data_alignment);
	case BYTE_ARRAY_TYPE:
		return align(array_size((byte_array*)this),data_alignment);
	case STRING_TYPE:
		return align(string_size(string_capacity((string*)this)),data_alignment);
	case TUPLE_TYPE:
		{
			tuple_layout *layout = (tuple_layout *)UNTAG(((tuple *)this)->layout);
			return align(tuple_size(layout),data_alignment);
		}
	case QUOTATION_TYPE:
		return align(sizeof(quotation),data_alignment);
	case WORD_TYPE:
		return align(sizeof(word),data_alignment);
	case FLOAT_TYPE:
		return align(sizeof(boxed_float),data_alignment);
	case DLL_TYPE:
		return align(sizeof(dll),data_alignment);
	case ALIEN_TYPE:
		return align(sizeof(alien),data_alignment);
	case WRAPPER_TYPE:
		return align(sizeof(wrapper),data_alignment);
	case CALLSTACK_TYPE:
		return align(callstack_size(untag_fixnum(((callstack *)this)->length)),data_alignment);
	default:
		critical_error("Invalid header",(cell)this);
		return 0; /* can't happen */
	}
}

/* The number of cells from the start of the object which should be scanned by
the GC. Some types have a binary payload at the end (string, word, DLL) which
we ignore. */
cell object::binary_payload_start() const
{
	if(free_p()) return 0;

	switch(type())
	{
	/* these objects do not refer to other objects at all */
	case FLOAT_TYPE:
	case BYTE_ARRAY_TYPE:
	case BIGNUM_TYPE:
	case CALLSTACK_TYPE:
		return 0;
	/* these objects have some binary data at the end */
	case WORD_TYPE:
		return sizeof(word) - sizeof(cell) * 3;
	case ALIEN_TYPE:
		return sizeof(cell) * 3;
	case DLL_TYPE:
		return sizeof(cell) * 2;
	case QUOTATION_TYPE:
		return sizeof(quotation) - sizeof(cell) * 2;
	case STRING_TYPE:
		return sizeof(string);
	/* everything else consists entirely of pointers */
	case ARRAY_TYPE:
		return array_size<array>(array_capacity((array*)this));
	case TUPLE_TYPE:
		return tuple_size(untag<tuple_layout>(((tuple *)this)->layout));
	case WRAPPER_TYPE:
		return sizeof(wrapper);
	default:
		critical_error("Invalid header",(cell)this);
                return 0; /* can't happen */
	}
}

data_heap_room factor_vm::data_room()
{
	data_heap_room room;

	room.nursery_size             = nursery.size;
	room.nursery_occupied         = nursery.occupied_space();
	room.nursery_free             = nursery.free_space();
	room.aging_size               = data->aging->size;
	room.aging_occupied           = data->aging->occupied_space();
	room.aging_free               = data->aging->free_space();
	room.tenured_size             = data->tenured->size;
	room.tenured_occupied         = data->tenured->occupied_space();
	room.tenured_total_free       = data->tenured->free_space();
	room.tenured_contiguous_free  = data->tenured->largest_free_block();
	room.tenured_free_block_count = data->tenured->free_block_count();
	room.cards                    = data->cards_end - data->cards;
	room.decks                    = data->decks_end - data->decks;
	room.mark_stack               = mark_stack.capacity() * sizeof(cell);

	return room;
}

void factor_vm::primitive_data_room()
{
	data_heap_room room = data_room();
	dpush(tag<byte_array>(byte_array_from_value(&room)));
}

struct object_accumulator {
	cell type;
	std::vector<cell> objects;

	explicit object_accumulator(cell type_) : type(type_) {}

	void operator()(object *obj)
	{
		if(type == TYPE_COUNT || obj->type() == type)
			objects.push_back(tag_dynamic(obj));
	}
};

cell factor_vm::instances(cell type)
{
	object_accumulator accum(type);
	each_object(accum);
	cell object_count = accum.objects.size();

	data_roots.push_back(data_root_range(&accum.objects[0],object_count));

	array *objects = allot_array(object_count,false_object);
	memcpy(objects->data(),&accum.objects[0],object_count * sizeof(cell));

	data_roots.pop_back();

	return tag<array>(objects);
}

void factor_vm::primitive_all_instances()
{
	primitive_full_gc();
	dpush(instances(TYPE_COUNT));
}

cell factor_vm::find_all_words()
{
	return instances(WORD_TYPE);
}

}
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  $RCSfile: appdata.hxx,v $
 *
 *  $Revision: 1.1.1.1 $
 *
 *  last change: $Author: hr $ $Date: 2000-09-18 16:52:33 $
 *
 *  The Contents of this file are made available subject to the terms of
 *  either of the following licenses
 *
 *         - GNU Lesser General Public License Version 2.1
 *         - Sun Industry Standards Source License Version 1.1
 *
 *  Sun Microsystems Inc., October, 2000
 *
 *  GNU Lesser General Public License Version 2.1
 *  =============================================
 *  Copyright 2000 by Sun Microsystems, Inc.
 *  901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License version 2.1, as published by the Free Software Foundation.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *  MA  02111-1307  USA
 *
 *
 *  Sun Industry Standards Source License Version 1.1
 *  =================================================
 *  The contents of this file are subject to the Sun Industry Standards
 *  Source License Version 1.1 (the "License"); You may not use this file
 *  except in compliance with the License. You may obtain a copy of the
 *  License at http://www.openoffice.org/license.html.
 *
 *  Software provided under this License is provided on an "AS IS" basis,
 *  WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
 *  WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
 *  MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
 *  See the License for the specific provisions governing your rights and
 *  obligations concerning the Software.
 *
 *  The Initial Developer of the Original Code is: Sun Microsystems, Inc.
 *
 *  Copyright: 2000 by Sun Microsystems, Inc.
 *
 *  All Rights Reserved.
 *
 *  Contributor(s): _______________________________________
 *
 *
 ************************************************************************/
#ifndef _SFX_APPDATA_HXX
#define _SFX_APPDATA_HXX

#include <tools/link.hxx>
#include <tools/list.hxx>
#include <svtools/lstner.hxx>
#include <bitset.hxx>
#include <objsh.hxx>

class SfxTaskManager;

class SfxApplication;
class SvBindingTransportFactory;
class SvLockBytesFactory;
class SfxIniDefaultManager;
class DataLockByteFactory_Impl;
class SvStrings;
class Config;
class PopupMenu;
class SfxBmkMenu;
class SvVerbList;
class SfxProgress;
class SfxConfigManager;
class SfxChildWinFactArr_Impl;
class SfxToolBoxConfig;
class SfxMacro;
class SfxDdeDocTopics_Impl;
class DdeService;
class SfxEventConfiguration;
class SfxMacroConfig;
class SvFactory;
class SotFactory;
class SfxItemPool;
class SfxInitLinkList;
class SfxFilterMatcher;
class DemoData_Impl;
class SfxExplorer;
class SfxMenuBarManager;
class StopButtonTimer_Impl;
class SvUShorts;
class SfxNodeData_Impl;
class SfxSIDList_Impl;
struct SfxFrameObjectFactoryPtr;
struct SfxPluginObjectFactoryPtr;
struct SfxPluginObjectFactoryPtr;
class ISfxTemplateCommon;
class SfxAnchorJobList_Impl;
class SfxFilterMatcher;
class INetConnection;
class SfxINetPlugInService;
class SfxTrash;
class SfxSimpleLockBytesFactoryMemberList;
class CntUpdateResults_Impl;
class SfxIniDefaultManager;
class SfxFolderCfgList_Impl;
class SfxCancelManager;
class ISfxModule;
struct SfxDownload_Impl;
class SvBindStatusCallback;
class SfxStatusDispatcher;
class SfxDesktop;
class SfxDdeTriggerTopic_Impl;
class OfaMiscCfg;
class SvLibrary;
class SfxDocumentTemplates;

DECLARE_LIST( ConnectionList_Impl, INetConnection * );

class StopButtonTimer_Impl : public Timer
{
    BOOL bState;
protected:
    virtual void Timeout();
public:
    StopButtonTimer_Impl();
    void SetButtonState( BOOL bStateP );
    BOOL GetButtonState() const { return bState; }
};

//=========================================================================
// SfxFolderState
//=========================================================================

/*
  [Beschreibung]
  Elemente dieser Aufzaehlung geben den Zustand eines Ordners an:
  SFX_FOLDERSTATE_EMPTY   der Ordner hat keine Unterordner
  SFX_FOLDERSTATE_CONTENT der Ordner hat Unterordner
  SFX_FOLDERSTATE_UNKNOWN es ist nicht bekannt, ob Unterordner vorhanden sind
  */

enum SfxFolderState
{
    SFX_FOLDERSTATE_EMPTY   = 0,
    SFX_FOLDERSTATE_CONTENT = 1,
    SFX_FOLDERSTATE_UNKNOWN = 2
};

//=========================================================================
// SfxAppData_Impl
//=========================================================================

class SfxFrameArr_Impl;

class SfxAppData_Impl : public SfxListener
{
public:
    SfxConfigManager*                   pAppCfg;
    SfxProgress*                        pProgress;
    SfxItemPool*                        pPool;
    SfxChildWinFactArr_Impl*            pFactArr;
    SfxMacro*                           pMacro;
    SvLibrary*                          pODKLib;
    String                              aLastDir;
    String                              aLastFilter;
    char                                nConfigManagerAvailable;
    IndexBitSet                         aIndexBitSet;
    DdeService*                         pDdeService; // wollen wir DDE machen?
    SfxDdeDocTopics_Impl*               pDocTopics;
    SfxEventConfiguration*              pEventConfig;
    SotFactory*                         pSfxApplicationObjectFactory;
    USHORT                              nAsynchronCalls;
    SvVerbList*                         pVerbs;
    USHORT                              nBasicCallLevel;
    USHORT                              nRescheduleLocks;
    USHORT                              nInReschedule;
    DemoData_Impl*                      pDemoData;
    SfxInitLinkList*                    pInitLinkList;
    Timer                               aLateInitTimer;
    SfxFilterMatcher*                   pMatcher;
    SfxExplorer*                        pExplorer;
    String                              aSaveAsTarget;
    String                              aUserEMailAddr;
    ConnectionList_Impl                 aConnectionList;
    SfxObjectFactory*                   pSfxPlugInObjectShellFactory;
    Window*                             pDefFocusWin;
    SfxMenuBarManager*                  pAppManager;
    SfxFrameObjectFactoryPtr*           pSfxFrameObjectFactoryPtr;
    List                                aPendingInitFactories;
    SfxIniDefaultManager*               pIniDefMgr;
    String                              aLogicAppName;
    SfxINetPlugInService*               pPlugService;
    StopButtonTimer_Impl*               pStopButtonTimer;
    SfxCancelManager*                   pCancelMgr;
    USHORT                              nDocModalMode;
    SvUShorts*                          pDisabledSlotList;
    Config*                             pFilterIni;
    ISfxModule*                         pISfxModule;
    String                              aLastNewURL;
    SfxPluginObjectFactoryPtr*          pSfxPluginObjectFactoryPtr;
    SfxNodeData_Impl*                   pNodeData_Impl;
    SfxSIDList_Impl*                    pSIDList_Impl;
    ISfxTemplateCommon*                 pTemplateCommon;
    Window*                             pActiveInplaceWindow;
    SfxAnchorJobList_Impl*              pAnchorJobList;
    ResMgr*                             pLabelResMgr;
    USHORT                              nDemoKind;
    SfxFrameArr_Impl*                   pTopFrames;
    SfxTrash*                           pTrash;
    SvStrings*                          pSecureURLs;
    USHORT                              nAutoTabPageId;
    DataLockByteFactory_Impl*           pDataLockBytesFactory;
    USHORT                              nExecutingSID;
    CntUpdateResults_Impl*              pNewMessages;
    USHORT                              nNewMessages;
    SvLockBytesFactory*                 pImageLockBytesFactory;
    SvLockBytesFactory*                 pInfoLockBytesFactory;
    SfxBmkMenu*                         pNewMenu;
    SfxBmkMenu*                         pBookmarkMenu;
    SfxBmkMenu*                         pAutoPilotMenu;
    SfxBmkMenu*                         pStartMenu;
    SfxStatusDispatcher*                pAppDispatch;
    SfxDdeTriggerTopic_Impl*            pTriggerTopic;
    DdeService*                         pDdeService2;
    SvStrings*                          pExtBrwOnExceptionList;
    SvStrings*                          pExtBrwOffExceptionList;
    OfaMiscCfg*                         pMiscConfig;
    SfxObjectShell*                     pThisDocument;
    BYTE                                bMultiQuickSearch;
    BYTE                                bShowFsysExtension;
    BYTE                                bUseExternBrowser;
    BOOL                                bAccelEnabled : 1;
    BOOL                                bIBMTitle : 1;
    BOOL                                bOLEResize : 1;
    BOOL                                bDirectAliveCount : 1;
    BOOL                                bInQuit : 1;
    BOOL                                bStbWasVisible : 1;
    BOOL                                bSessionFailed : 1;
    BOOL                                bOLEAutomation : 1;
    BOOL                                bInvalidateOnUnlock : 1;
    BOOL                                bBean : 1;
    BOOL                                bMinimized : 1;
    BOOL                                bInvisible : 1;
    BOOL                                bSmartBeamer : 1;
    BOOL                                bInException : 1;
    BOOL                                bNewMessagesBlinker : 1;
    BOOL                                bNewTaskForNewMessages : 1;
    BOOL                                bBeamerSwitchedOn : 1;
    BOOL                                bLateInit_BrowseRegistrationPage : 1;
    USHORT                              nAppEvent;
    SfxDocumentTemplates*               pTemplates;
    String                              aOpenList;
    String                              aPrintList;
    String                              aUcbUrl;

    SfxAppData_Impl( SfxApplication* pApp );
    ~SfxAppData_Impl();

    PopupMenu*                          GetPopupMenu( USHORT nSid, BOOL bBig=FALSE, BOOL bNew=FALSE );
    virtual void                        Notify( SfxBroadcaster &rBC, const SfxHint &rHint );
    DECL_STATIC_LINK(                   SfxAppData_Impl, CreateDataLockBytesFactory, void* );
    void                                ResetNewMessages( const String &rFolderULR );
    void                                LoadNewMessages();
    void                                SaveNewMessages();
    void                                UpdateApplicationSettings( BOOL bDontHide );
    SfxDocumentTemplates*               GetDocumentTemplates();
};

extern void FATToVFat_Impl( String& );

#include <svtools/poolitem.hxx>

class SfxPtrItem : public SfxPoolItem
{
    void* pPtr;
public:
                             TYPEINFO();
    virtual SfxPoolItem*     Clone( SfxItemPool *pPool = 0 ) const
    {   return new SfxPtrItem( *this ); }
    virtual int              operator==( const SfxPoolItem& rL) const
    {   return ((SfxPtrItem&)rL).pPtr == pPtr; }
    SfxPtrItem( USHORT nWhich, void * pValue ) : SfxPoolItem( nWhich )
    {   pPtr = pValue; }
    void* GetValue() const { return pPtr; }
};

#endif // #ifndef _SFX_APPDATA_HXX

<commit_msg>Cleanup; new Options classes<commit_after>/*************************************************************************
 *
 *  $RCSfile: appdata.hxx,v $
 *
 *  $Revision: 1.2 $
 *
 *  last change: $Author: mba $ $Date: 2000-09-28 11:29:31 $
 *
 *  The Contents of this file are made available subject to the terms of
 *  either of the following licenses
 *
 *         - GNU Lesser General Public License Version 2.1
 *         - Sun Industry Standards Source License Version 1.1
 *
 *  Sun Microsystems Inc., October, 2000
 *
 *  GNU Lesser General Public License Version 2.1
 *  =============================================
 *  Copyright 2000 by Sun Microsystems, Inc.
 *  901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License version 2.1, as published by the Free Software Foundation.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *  MA  02111-1307  USA
 *
 *
 *  Sun Industry Standards Source License Version 1.1
 *  =================================================
 *  The contents of this file are subject to the Sun Industry Standards
 *  Source License Version 1.1 (the "License"); You may not use this file
 *  except in compliance with the License. You may obtain a copy of the
 *  License at http://www.openoffice.org/license.html.
 *
 *  Software provided under this License is provided on an "AS IS" basis,
 *  WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
 *  WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
 *  MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
 *  See the License for the specific provisions governing your rights and
 *  obligations concerning the Software.
 *
 *  The Initial Developer of the Original Code is: Sun Microsystems, Inc.
 *
 *  Copyright: 2000 by Sun Microsystems, Inc.
 *
 *  All Rights Reserved.
 *
 *  Contributor(s): _______________________________________
 *
 *
 ************************************************************************/
#ifndef _SFX_APPDATA_HXX
#define _SFX_APPDATA_HXX

#include <tools/link.hxx>
#include <tools/list.hxx>
#include <svtools/lstner.hxx>
#include <vcl/timer.hxx>
#include <tools/string.hxx>

#include "bitset.hxx"

class SfxApplication;
class SvStrings;
class Config;
class PopupMenu;
class SfxBmkMenu;
class SvVerbList;
class SfxProgress;
class SfxConfigManager;
class SfxChildWinFactArr_Impl;
class SfxToolBoxConfig;
class SfxDdeDocTopics_Impl;
class DdeService;
class SfxEventConfiguration;
class SfxMacroConfig;
class SfxItemPool;
class SfxInitLinkList;
class SfxFilterMatcher;
class SvUShorts;
struct SfxFrameObjectFactoryPtr;
struct SfxPluginObjectFactoryPtr;
class ISfxTemplateCommon;
class SfxFilterMatcher;
class SfxCancelManager;
class SfxStatusDispatcher;
class SfxDdeTriggerTopic_Impl;
class OfaMiscCfg;
class SfxDocumentTemplates;
class SfxFrameArr_Impl;
class SvtSaveOptions;
class SvtUndoOptions;
class SvtHelpOptions;
class SfxObjectFactory;
class SfxObjectShell;
class ResMgr;
class Window;

class StopButtonTimer_Impl : public Timer
{
    BOOL bState;
protected:
    virtual void Timeout();
public:
    StopButtonTimer_Impl();
    void SetButtonState( BOOL bStateP );
    BOOL GetButtonState() const { return bState; }
};

//=========================================================================
// SfxAppData_Impl
//=========================================================================

class SfxAppData_Impl : public SfxListener
{
public:
    IndexBitSet                         aIndexBitSet;           // for counting noname documents
    List                                aPendingInitFactories;  // late filter init
    Timer                               aLateInitTimer;
    String                              aLastDir;               // for IO dialog
    String                              aLastFilter;            // for IO dialog
    String                              aLastNewURL;            // for AppControl
    String                              aOpenList;              // command line arguments
    String                              aPrintList;             // command line arguments
    String                              aUcbUrl;                // command line arguments

    // DDE stuff
    DdeService*                         pDdeService;
    SfxDdeDocTopics_Impl*               pDocTopics;
    SfxDdeTriggerTopic_Impl*            pTriggerTopic;
    DdeService*                         pDdeService2;

    // single instance classes
    SfxChildWinFactArr_Impl*            pFactArr;
    SfxPluginObjectFactoryPtr*          pSfxPluginObjectFactoryPtr;
    SfxObjectFactory*                   pSfxPlugInObjectShellFactory;
    SfxFrameObjectFactoryPtr*           pSfxFrameObjectFactoryPtr;
    SfxFrameArr_Impl*                   pTopFrames;

    // special members
    SfxInitLinkList*                    pInitLinkList;
    StopButtonTimer_Impl*               pStopButtonTimer;

    // application members
    SfxFilterMatcher*                   pMatcher;
    SfxCancelManager*                   pCancelMgr;
    ResMgr*                             pLabelResMgr;
    SfxStatusDispatcher*                pAppDispatch;
    SfxConfigManager*                   pAppCfg;
    SfxDocumentTemplates*               pTemplates;

    // global pointers
    SvVerbList*                         pVerbs;
    Config*                             pFilterIni;
    SfxItemPool*                        pPool;
    SfxEventConfiguration*              pEventConfig;
    SvUShorts*                          pDisabledSlotList;
    SvStrings*                          pSecureURLs;
    SfxBmkMenu*                         pNewMenu;
    SfxBmkMenu*                         pAutoPilotMenu;
    OfaMiscCfg*                         pMiscConfig;
    SvtSaveOptions*                     pSaveOptions;
    SvtUndoOptions*                     pUndoOptions;
    SvtHelpOptions*                     pHelpOptions;

    // "current" functionality
    SfxObjectShell*                     pThisDocument;
    SfxProgress*                        pProgress;
    Window*                             pDefFocusWin;
    ISfxTemplateCommon*                 pTemplateCommon;

    USHORT                              nDocModalMode;              // counts documents in modal mode
    USHORT                              nAutoTabPageId;
    USHORT                              nExecutingSID;
    USHORT                              nBasicCallLevel;
    USHORT                              nRescheduleLocks;
    USHORT                              nInReschedule;
    USHORT                              nAsynchronCalls;
    USHORT                              nAppEvent;                  // command line interpretation

    BOOL                                bDirectAliveCount : 1;
    BOOL                                bInQuit : 1;
    BOOL                                bInvalidateOnUnlock : 1;
    BOOL                                bBean : 1;
    BOOL                                bMinimized : 1;
    BOOL                                bInvisible : 1;
    BOOL                                bInException : 1;
    BOOL                                bPlugged : 1;
    BOOL                                bOLEResize : 1;

                                        SfxAppData_Impl( SfxApplication* );
                                        ~SfxAppData_Impl();

    PopupMenu*                          GetPopupMenu( USHORT nSid, BOOL bBig=FALSE, BOOL bNew=FALSE );
    virtual void                        Notify( SfxBroadcaster &rBC, const SfxHint &rHint );
    void                                UpdateApplicationSettings( BOOL bDontHide );
    SfxDocumentTemplates*               GetDocumentTemplates();
    DECL_STATIC_LINK(                   SfxAppData_Impl, CreateDocumentTemplates, void* );
};

#endif // #ifndef _SFX_APPDATA_HXX

<|endoftext|>


<commit_before><commit_msg>A set of patches from Kein-Hong Man to improve handling of barewords, numbers, special variables, and here documents.<commit_after><|endoftext|>


<commit_before>#include <../recurse.hpp>
#include <QHash>

int main(int argc, char *argv[])
{
    Recurse app(argc, argv);

    // http options
    QHash<QString, QVariant> http_options;
    http_options["port"] = 3000;

    // https options
    QHash<QString, QVariant> https_options;
    https_options["port"] = 3020;
    https_options["private_key"] = "./priv.pem";
    https_options["certificate"] = "./cert.pem";

    app.http_server(http_options);
    app.https_server(https_options);

    app.use([](auto &ctx, auto next) {
        qDebug() << "got a new request from" << ctx.request.ip;
        next();
    });

    app.use([](auto &ctx) {
        ctx.response.send("Hello, world");
    });

    qDebug() << "start listening...";

    auto ret = app.listen();
    if (ret.error()) {
        qDebug() << "error upon listening:" << ret.lastError();
    }
};
<commit_msg>example: remove extra ;<commit_after>#include <../recurse.hpp>
#include <QHash>

int main(int argc, char *argv[])
{
    Recurse app(argc, argv);

    // http options
    QHash<QString, QVariant> http_options;
    http_options["port"] = 3000;

    // https options
    QHash<QString, QVariant> https_options;
    https_options["port"] = 3020;
    https_options["private_key"] = "./priv.pem";
    https_options["certificate"] = "./cert.pem";

    app.http_server(http_options);
    app.https_server(https_options);

    app.use([](auto &ctx, auto next) {
        qDebug() << "got a new request from" << ctx.request.ip;
        next();
    });

    app.use([](auto &ctx) {
        ctx.response.send("Hello, world");
    });

    qDebug() << "start listening...";

    auto ret = app.listen();
    if (ret.error()) {
        qDebug() << "error upon listening:" << ret.lastError();
    }
}
<|endoftext|>


<commit_before><commit_msg>Changed ListBox::Clear() only to detach/attach the header row if it was already attached.<commit_after><|endoftext|>


<commit_before>// Copyright (c) 2012 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 <gtest/gtest.h>

#include <string>
#include <sys/wait.h>

#include "base/bind.h"
#include "base/eintr_wrapper.h"
#include "base/memory/scoped_ptr.h"
#include "base/message_loop.h"
#include "base/process_util.h"
#include "base/synchronization/waitable_event.h"
#include "base/threading/thread.h"
#include "chrome/browser/chromeos/process_proxy/process_proxy_registry.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "content/public/browser/browser_thread.h"

using content::BrowserThread;

namespace {

// The test line must have all distinct characters.
const char kTestLineToSend[] = "abcdefgh\n";
const char kTestLineExpected[] = "abcdefgh\r\n";

const char kCatCommand[] = "cat";
const char kStdoutType[] = "stdout";
const int kTestLineNum = 100;

class TestRunner {
 public:
  virtual ~TestRunner() {}
  virtual void SetupExpectations(pid_t pid) = 0;
  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) = 0;
  virtual void StartRegistryTest(ProcessProxyRegistry* registry) = 0;

 protected:
  pid_t pid_;
};

class RegistryTestRunner : public TestRunner {
 public:
  virtual ~RegistryTestRunner() {}

  virtual void SetupExpectations(pid_t pid) OVERRIDE {
    pid_ = pid;
    left_to_check_index_[0] = 0;
    left_to_check_index_[1] = 0;
    // We consider that a line processing has started if a value in
    // left_to_check__[index] is set to 0, thus -2.
    lines_left_ = 2 * kTestLineNum - 2;
    expected_line_ = kTestLineExpected;
  }

  // Method to test validity of received input. We will receive two streams of
  // the same data. (input will be echoed twice by the testing process). Each
  // stream will contain the same string repeated |kTestLineNum| times. So we
  // have to match 2 * |kTestLineNum| lines. The problem is the received lines
  // from different streams may be interleaved (e.g. we may receive
  // abc|abcdef|defgh|gh). To deal with that, we allow to test received text
  // against two lines. The lines MUST NOT have two same characters for this
  // algorithm to work.
  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) OVERRIDE {
    EXPECT_EQ(type, kStdoutType);
    EXPECT_EQ(pid_, pid);

    bool valid = true;
    for (size_t i = 0; i < output.length(); i++) {
      // The character output[i] should be next in at least one of the lines we
      // are testing.
      valid = (ProcessReceivedCharacter(output[i], 0) ||
               ProcessReceivedCharacter(output[i], 1));
      EXPECT_TRUE(valid) << "Received: " << output;
    }

    if (!valid || TestSucceeded()) {
      content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                       MessageLoop::QuitClosure());
    }
  }

  virtual void StartRegistryTest(ProcessProxyRegistry* registry) OVERRIDE {
    for (int i = 0; i < kTestLineNum; i++) {
      EXPECT_TRUE(registry->SendInput(pid_, kTestLineToSend));
    }
  }

 private:
  bool ProcessReceivedCharacter(char received, size_t stream) {
    if (stream < 0 || stream >= arraysize(left_to_check_index_))
      return false;
    bool success = left_to_check_index_[stream] < expected_line_.length() &&
                   expected_line_[left_to_check_index_[stream]] == received;
    if (success)
      left_to_check_index_[stream]++;
    if (left_to_check_index_[stream] == expected_line_.length() &&
        lines_left_ > 0) {
      // Take another line to test for this stream, if there are any lines left.
      // If not, this stream is done.
      left_to_check_index_[stream] = 0;
      lines_left_--;
    }
    return success;
  }

  bool TestSucceeded() {
    return left_to_check_index_[0] == expected_line_.length() &&
           left_to_check_index_[1] == expected_line_.length() &&
           lines_left_ == 0;
  }

  size_t left_to_check_index_[2];
  size_t lines_left_;
  std::string expected_line_;
};

class RegistryNotifiedOnProcessExitTestRunner : public TestRunner {
 public:
  virtual ~RegistryNotifiedOnProcessExitTestRunner() {}

  virtual void SetupExpectations(pid_t pid) OVERRIDE {
    output_received_ = false;
    pid_ = pid;
  }

  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) OVERRIDE {
    EXPECT_EQ(pid_, pid);
    if (!output_received_) {
      output_received_ = true;
      EXPECT_EQ(type, "stdout");
      EXPECT_EQ(output, "p");
      base::KillProcess(pid_, 0 , true);
      return;
    }
    EXPECT_EQ("exit", type);
    content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                     MessageLoop::QuitClosure());
  }

  virtual void StartRegistryTest(ProcessProxyRegistry* registry) {
    EXPECT_TRUE(registry->SendInput(pid_, "p"));
  }

 private:
  bool output_received_;
};

class SigIntTestRunner : public TestRunner {
 public:
  virtual ~SigIntTestRunner() {}

  virtual void SetupExpectations(pid_t pid) OVERRIDE {
    pid_ = pid;
  }

  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) OVERRIDE {
    EXPECT_EQ(pid_, pid);
    // We may receive ^C on stdout, but we don't care about that, as long as we
    // eventually received exit event.
    if (type == "exit") {
      content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                       MessageLoop::QuitClosure());
    }
 }

  virtual void StartRegistryTest(ProcessProxyRegistry* registry) {
    // Send SingInt and verify the process exited.
    EXPECT_TRUE(registry->SendInput(pid_, "\003"));
  }

 private:
  bool output_received_;
};

}  // namespace

class ProcessProxyTest : public InProcessBrowserTest {
 public:
  ProcessProxyTest() {}
  ~ProcessProxyTest() {}

 protected:
  void InitRegistryTest() {
    registry_ = ProcessProxyRegistry::Get();

    EXPECT_TRUE(registry_->OpenProcess(kCatCommand, &pid_,
        base::Bind(&TestRunner::OnSomeRead,
                   base::Unretained(test_runner_.get()))));

    test_runner_->SetupExpectations(pid_);
    test_runner_->StartRegistryTest(registry_);
  }

  void EndRegistryTest() {
    registry_->CloseProcess(pid_);

    base::TerminationStatus status = base::GetTerminationStatus(pid_, NULL);
    EXPECT_NE(base::TERMINATION_STATUS_STILL_RUNNING, status);
    if (status == base::TERMINATION_STATUS_STILL_RUNNING)
      base::KillProcess(pid_, 0, true);

    content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                     MessageLoop::QuitClosure());
  }

  void RunTest() {
    BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
         base::Bind(&ProcessProxyTest::InitRegistryTest,
                    base::Unretained(this)));

    // Wait until all data from output watcher is received (QuitTask will be
    // fired on watcher thread).
    ui_test_utils::RunMessageLoop();

    BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
         base::Bind(&ProcessProxyTest::EndRegistryTest,
                    base::Unretained(this)));

    // Wait until we clean up the process proxy.
    ui_test_utils::RunMessageLoop();
  }

  scoped_ptr<TestRunner> test_runner_;

 private:
  ProcessProxyRegistry* registry_;
  pid_t pid_;
};

// Test will open new process that will run cat command, and verify data we
// write to process gets echoed back.
IN_PROC_BROWSER_TEST_F(ProcessProxyTest, RegistryTest) {
  test_runner_.reset(new RegistryTestRunner());
  RunTest();
}

// Open new process, then kill it. Verifiy that we detect when the process dies.
IN_PROC_BROWSER_TEST_F(ProcessProxyTest, RegistryNotifiedOnProcessExit) {
  test_runner_.reset(new RegistryNotifiedOnProcessExitTestRunner());
  RunTest();
}

// Test verifies that \003 message send to process is processed as SigInt.
// Timing out on the waterfall: http://crbug.com/115064
IN_PROC_BROWSER_TEST_F(ProcessProxyTest, DISABLED_SigInt) {
  test_runner_.reset(new SigIntTestRunner());
  RunTest();
}
<commit_msg>Fix clang compile error<commit_after>// Copyright (c) 2012 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 <gtest/gtest.h>

#include <string>
#include <sys/wait.h>

#include "base/bind.h"
#include "base/eintr_wrapper.h"
#include "base/memory/scoped_ptr.h"
#include "base/message_loop.h"
#include "base/process_util.h"
#include "base/synchronization/waitable_event.h"
#include "base/threading/thread.h"
#include "chrome/browser/chromeos/process_proxy/process_proxy_registry.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "content/public/browser/browser_thread.h"

using content::BrowserThread;

namespace {

// The test line must have all distinct characters.
const char kTestLineToSend[] = "abcdefgh\n";
const char kTestLineExpected[] = "abcdefgh\r\n";

const char kCatCommand[] = "cat";
const char kStdoutType[] = "stdout";
const int kTestLineNum = 100;

class TestRunner {
 public:
  virtual ~TestRunner() {}
  virtual void SetupExpectations(pid_t pid) = 0;
  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) = 0;
  virtual void StartRegistryTest(ProcessProxyRegistry* registry) = 0;

 protected:
  pid_t pid_;
};

class RegistryTestRunner : public TestRunner {
 public:
  virtual ~RegistryTestRunner() {}

  virtual void SetupExpectations(pid_t pid) OVERRIDE {
    pid_ = pid;
    left_to_check_index_[0] = 0;
    left_to_check_index_[1] = 0;
    // We consider that a line processing has started if a value in
    // left_to_check__[index] is set to 0, thus -2.
    lines_left_ = 2 * kTestLineNum - 2;
    expected_line_ = kTestLineExpected;
  }

  // Method to test validity of received input. We will receive two streams of
  // the same data. (input will be echoed twice by the testing process). Each
  // stream will contain the same string repeated |kTestLineNum| times. So we
  // have to match 2 * |kTestLineNum| lines. The problem is the received lines
  // from different streams may be interleaved (e.g. we may receive
  // abc|abcdef|defgh|gh). To deal with that, we allow to test received text
  // against two lines. The lines MUST NOT have two same characters for this
  // algorithm to work.
  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) OVERRIDE {
    EXPECT_EQ(type, kStdoutType);
    EXPECT_EQ(pid_, pid);

    bool valid = true;
    for (size_t i = 0; i < output.length(); i++) {
      // The character output[i] should be next in at least one of the lines we
      // are testing.
      valid = (ProcessReceivedCharacter(output[i], 0) ||
               ProcessReceivedCharacter(output[i], 1));
      EXPECT_TRUE(valid) << "Received: " << output;
    }

    if (!valid || TestSucceeded()) {
      content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                       MessageLoop::QuitClosure());
    }
  }

  virtual void StartRegistryTest(ProcessProxyRegistry* registry) OVERRIDE {
    for (int i = 0; i < kTestLineNum; i++) {
      EXPECT_TRUE(registry->SendInput(pid_, kTestLineToSend));
    }
  }

 private:
  bool ProcessReceivedCharacter(char received, size_t stream) {
    if (stream >= arraysize(left_to_check_index_))
      return false;
    bool success = left_to_check_index_[stream] < expected_line_.length() &&
                   expected_line_[left_to_check_index_[stream]] == received;
    if (success)
      left_to_check_index_[stream]++;
    if (left_to_check_index_[stream] == expected_line_.length() &&
        lines_left_ > 0) {
      // Take another line to test for this stream, if there are any lines left.
      // If not, this stream is done.
      left_to_check_index_[stream] = 0;
      lines_left_--;
    }
    return success;
  }

  bool TestSucceeded() {
    return left_to_check_index_[0] == expected_line_.length() &&
           left_to_check_index_[1] == expected_line_.length() &&
           lines_left_ == 0;
  }

  size_t left_to_check_index_[2];
  size_t lines_left_;
  std::string expected_line_;
};

class RegistryNotifiedOnProcessExitTestRunner : public TestRunner {
 public:
  virtual ~RegistryNotifiedOnProcessExitTestRunner() {}

  virtual void SetupExpectations(pid_t pid) OVERRIDE {
    output_received_ = false;
    pid_ = pid;
  }

  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) OVERRIDE {
    EXPECT_EQ(pid_, pid);
    if (!output_received_) {
      output_received_ = true;
      EXPECT_EQ(type, "stdout");
      EXPECT_EQ(output, "p");
      base::KillProcess(pid_, 0 , true);
      return;
    }
    EXPECT_EQ("exit", type);
    content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                     MessageLoop::QuitClosure());
  }

  virtual void StartRegistryTest(ProcessProxyRegistry* registry) {
    EXPECT_TRUE(registry->SendInput(pid_, "p"));
  }

 private:
  bool output_received_;
};

class SigIntTestRunner : public TestRunner {
 public:
  virtual ~SigIntTestRunner() {}

  virtual void SetupExpectations(pid_t pid) OVERRIDE {
    pid_ = pid;
  }

  virtual void OnSomeRead(pid_t pid, const std::string& type,
                          const std::string& output) OVERRIDE {
    EXPECT_EQ(pid_, pid);
    // We may receive ^C on stdout, but we don't care about that, as long as we
    // eventually received exit event.
    if (type == "exit") {
      content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                       MessageLoop::QuitClosure());
    }
 }

  virtual void StartRegistryTest(ProcessProxyRegistry* registry) {
    // Send SingInt and verify the process exited.
    EXPECT_TRUE(registry->SendInput(pid_, "\003"));
  }

 private:
  bool output_received_;
};

}  // namespace

class ProcessProxyTest : public InProcessBrowserTest {
 public:
  ProcessProxyTest() {}
  ~ProcessProxyTest() {}

 protected:
  void InitRegistryTest() {
    registry_ = ProcessProxyRegistry::Get();

    EXPECT_TRUE(registry_->OpenProcess(kCatCommand, &pid_,
        base::Bind(&TestRunner::OnSomeRead,
                   base::Unretained(test_runner_.get()))));

    test_runner_->SetupExpectations(pid_);
    test_runner_->StartRegistryTest(registry_);
  }

  void EndRegistryTest() {
    registry_->CloseProcess(pid_);

    base::TerminationStatus status = base::GetTerminationStatus(pid_, NULL);
    EXPECT_NE(base::TERMINATION_STATUS_STILL_RUNNING, status);
    if (status == base::TERMINATION_STATUS_STILL_RUNNING)
      base::KillProcess(pid_, 0, true);

    content::BrowserThread::PostTask(content::BrowserThread::UI, FROM_HERE,
                                     MessageLoop::QuitClosure());
  }

  void RunTest() {
    BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
         base::Bind(&ProcessProxyTest::InitRegistryTest,
                    base::Unretained(this)));

    // Wait until all data from output watcher is received (QuitTask will be
    // fired on watcher thread).
    ui_test_utils::RunMessageLoop();

    BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
         base::Bind(&ProcessProxyTest::EndRegistryTest,
                    base::Unretained(this)));

    // Wait until we clean up the process proxy.
    ui_test_utils::RunMessageLoop();
  }

  scoped_ptr<TestRunner> test_runner_;

 private:
  ProcessProxyRegistry* registry_;
  pid_t pid_;
};

// Test will open new process that will run cat command, and verify data we
// write to process gets echoed back.
IN_PROC_BROWSER_TEST_F(ProcessProxyTest, RegistryTest) {
  test_runner_.reset(new RegistryTestRunner());
  RunTest();
}

// Open new process, then kill it. Verifiy that we detect when the process dies.
IN_PROC_BROWSER_TEST_F(ProcessProxyTest, RegistryNotifiedOnProcessExit) {
  test_runner_.reset(new RegistryNotifiedOnProcessExitTestRunner());
  RunTest();
}

// Test verifies that \003 message send to process is processed as SigInt.
// Timing out on the waterfall: http://crbug.com/115064
IN_PROC_BROWSER_TEST_F(ProcessProxyTest, DISABLED_SigInt) {
  test_runner_.reset(new SigIntTestRunner());
  RunTest();
}
<|endoftext|>


<commit_before>#include "pjobrunnerpool.h"
#include <assert.h>
#include <iostream>

PJobRunnerPool::PJobRunnerPool()
{
    connect(&m_scanner, SIGNAL(found_pjob_runner(PJobRunnerSessionWrapper*)), this, SLOT(found_pjob_runner(PJobRunnerSessionWrapper*)));
    connect(&m_scanner, SIGNAL(finished_scanning()), this, SLOT(search_finished()));
    connect(&m_scanner, SIGNAL(probing_host(QHostAddress)), this, SLOT(scanner_is_probing(QHostAddress)));
}

PJobRunnerPool& PJobRunnerPool::instance(){
    static PJobRunnerPool pool;
    return pool;
}

QList<QHostAddress> PJobRunnerPool::known_pjob_runners() const{
    return m_known_pjob_runners;
}

void PJobRunnerPool::start_search_network(const QNetworkInterface& i){
    m_backup_list = m_known_pjob_runners;
    if(!m_scanner.isRunning()){
        m_scanner.set_network_interface(i);
        emit network_scan_started();
        m_scanner.start();
    }
}

void PJobRunnerPool::stop_search_network(){
    m_scanner.stop_scan();
}

void PJobRunnerPool::found_pjob_runner(PJobRunnerSessionWrapper* session){
    QHostAddress new_peer = session->peer();
    if(!m_info_sessions.contains(new_peer)){
        m_info_sessions[new_peer] = session;
    }else delete session;
    if(!m_known_pjob_runners.contains(new_peer)){
        m_known_pjob_runners.append(new_peer);
        emit found_new_pjob_runner(new_peer);
    }
}

void PJobRunnerPool::search_finished(){
    foreach(QHostAddress host, m_backup_list){
        if(!m_known_pjob_runners.contains(host))
            emit lost_pjob_runner(host);
    }
    emit network_scan_finished();
}

void PJobRunnerPool::scanner_is_probing(QHostAddress host){
    emit probing_host(host);
}

QString PJobRunnerPool::hostname(QHostAddress host) const{
    assert(m_info_sessions.contains(host));
    return m_info_sessions[host]->hostname();
}

QString PJobRunnerPool::platform(QHostAddress host) const{
    assert(m_info_sessions.contains(host));
    return m_info_sessions[host]->platform();
}

unsigned int PJobRunnerPool::max_thread_count() const{
    unsigned int count = 0;
    foreach(QHostAddress host, m_known_pjob_runners){
        try{
            PJobRunnerSessionWrapper session(host);
            count += session.max_process_count();
        }catch(...){
            std::cout << "Ups!" << std::endl;
        }
    }
    return count;
}

bool PJobRunnerPool::is_scanning(){
    return m_scanner.isRunning();
}

unsigned int PJobRunnerPool::max_thread_count_for_host(QHostAddress host) const{
    QHash<QHostAddress, PJobRunnerSessionWrapper*>::const_iterator it = m_info_sessions.find(host);
    if(it == m_info_sessions.end()){
        try{
            PJobRunnerSessionWrapper session(host);
            return session.max_process_count();
        }catch(...){
            std::cout << "Ups2!" << std::endl;
        }
    }
    return it.value()->max_process_count();
}

unsigned int PJobRunnerPool::thread_count_for_host(QHostAddress host) const{
    unsigned int retries = 0;
    while(retries < 3){
        try{
            QHash<QHostAddress, PJobRunnerSessionWrapper*>::const_iterator it = m_info_sessions.find(host);
            if(it == m_info_sessions.end()){
                PJobRunnerSessionWrapper session(host);
                return session.process_count();
            }
            return it.value()->process_count();
        }catch(LostConnectionException e){
            retries++;
        }
    }
    return 0;
}

unsigned int PJobRunnerPool::thread_count() const{
    unsigned int count=0;
    foreach(QHostAddress host, known_pjob_runners()){
        count += thread_count_for_host(host);
    }
    return count;
}

void PJobRunnerPool::remove(QHostAddress host){
    m_known_pjob_runners.removeOne(host);
    m_info_sessions.remove(host);
}
<commit_msg>Uncaught exception fix.<commit_after>#include "pjobrunnerpool.h"
#include <assert.h>
#include <iostream>

PJobRunnerPool::PJobRunnerPool()
{
    connect(&m_scanner, SIGNAL(found_pjob_runner(PJobRunnerSessionWrapper*)), this, SLOT(found_pjob_runner(PJobRunnerSessionWrapper*)));
    connect(&m_scanner, SIGNAL(finished_scanning()), this, SLOT(search_finished()));
    connect(&m_scanner, SIGNAL(probing_host(QHostAddress)), this, SLOT(scanner_is_probing(QHostAddress)));
}

PJobRunnerPool& PJobRunnerPool::instance(){
    static PJobRunnerPool pool;
    return pool;
}

QList<QHostAddress> PJobRunnerPool::known_pjob_runners() const{
    return m_known_pjob_runners;
}

void PJobRunnerPool::start_search_network(const QNetworkInterface& i){
    m_backup_list = m_known_pjob_runners;
    if(!m_scanner.isRunning()){
        m_scanner.set_network_interface(i);
        emit network_scan_started();
        m_scanner.start();
    }
}

void PJobRunnerPool::stop_search_network(){
    m_scanner.stop_scan();
}

void PJobRunnerPool::found_pjob_runner(PJobRunnerSessionWrapper* session){
    QHostAddress new_peer = session->peer();
    if(!m_info_sessions.contains(new_peer)){
        m_info_sessions[new_peer] = session;
    }else delete session;
    if(!m_known_pjob_runners.contains(new_peer)){
        m_known_pjob_runners.append(new_peer);
        emit found_new_pjob_runner(new_peer);
    }
}

void PJobRunnerPool::search_finished(){
    foreach(QHostAddress host, m_backup_list){
        if(!m_known_pjob_runners.contains(host))
            emit lost_pjob_runner(host);
    }
    emit network_scan_finished();
}

void PJobRunnerPool::scanner_is_probing(QHostAddress host){
    emit probing_host(host);
}

QString PJobRunnerPool::hostname(QHostAddress host) const{
    assert(m_info_sessions.contains(host));
    return m_info_sessions[host]->hostname();
}

QString PJobRunnerPool::platform(QHostAddress host) const{
    assert(m_info_sessions.contains(host));
    return m_info_sessions[host]->platform();
}

unsigned int PJobRunnerPool::max_thread_count() const{
    unsigned int count = 0;
    foreach(QHostAddress host, m_known_pjob_runners){
        try{
            PJobRunnerSessionWrapper session(host);
            count += session.max_process_count();
        }catch(...){
            std::cout << "Ups!" << std::endl;
        }
    }
    return count;
}

bool PJobRunnerPool::is_scanning(){
    return m_scanner.isRunning();
}

unsigned int PJobRunnerPool::max_thread_count_for_host(QHostAddress host) const{
    QHash<QHostAddress, PJobRunnerSessionWrapper*>::const_iterator it = m_info_sessions.find(host);
    if(it == m_info_sessions.end()){
        try{
            PJobRunnerSessionWrapper session(host);
            return session.max_process_count();
        }catch(...){
            std::cout << "Ups2!" << std::endl;
        }
    }
    return it.value()->max_process_count();
}

unsigned int PJobRunnerPool::thread_count_for_host(QHostAddress host) const{
    unsigned int retries = 0;
    while(retries < 3){
        try{
            QHash<QHostAddress, PJobRunnerSessionWrapper*>::const_iterator it = m_info_sessions.find(host);
            if(it == m_info_sessions.end()){
                PJobRunnerSessionWrapper session(host);
                return session.process_count();
            }
            return it.value()->process_count();
        }catch(LostConnectionException e){
            retries++;
        }catch(QString s){
            retries++;
        }

    }
    return 0;
}

unsigned int PJobRunnerPool::thread_count() const{
    unsigned int count=0;
    foreach(QHostAddress host, known_pjob_runners()){
        count += thread_count_for_host(host);
    }
    return count;
}

void PJobRunnerPool::remove(QHostAddress host){
    m_known_pjob_runners.removeOne(host);
    m_info_sessions.remove(host);
}
<|endoftext|>


<commit_before>#include "sajson.h"
#include <assert.h>

using namespace sajson;

inline bool success(const document& doc) {
    if (!doc.is_valid()) {
        fprintf(stderr, "%s\n", doc.get_error_message_as_cstring());
        return false;
    }
    return true;
}

struct jsonstats {
    jsonstats()
        : null_count(0)
        , false_count(0)
        , true_count(0)
        , number_count(0)
        , object_count(0)
        , array_count(0)
        , string_count(0)
        , total_string_length(0)
        , total_array_length(0)
        , total_object_length(0)
        , total_number_value(0) {}

    size_t null_count;
    size_t false_count;
    size_t true_count;
    size_t number_count;
    size_t object_count;
    size_t array_count;
    size_t string_count;

    size_t total_string_length;
    size_t total_array_length;
    size_t total_object_length;
    double total_number_value;
};

void traverse(jsonstats& stats, const sajson::value& node) {
    using namespace sajson;

    switch (node.get_type()) {
    case TYPE_NULL:
        ++stats.null_count;
        break;

    case TYPE_FALSE:
        ++stats.false_count;
        break;

    case TYPE_TRUE:
        ++stats.true_count;
        break;

    case TYPE_ARRAY: {
        ++stats.array_count;
        auto length = node.get_length();
        stats.total_array_length += length;
        for (size_t i = 0; i < length; ++i) {
            traverse(stats, node.get_array_element(i));
        }
        break;
    }

    case TYPE_OBJECT: {
        ++stats.object_count;
        auto length = node.get_length();
        stats.total_object_length += length;
        for (auto i = 0u; i < length; ++i) {
            traverse(stats, node.get_object_value(i));
        }
        break;
    }

    case TYPE_STRING:
        ++stats.string_count;
        stats.total_string_length += node.get_string_length();
        break;

    case TYPE_DOUBLE:
    case TYPE_INTEGER:
        ++stats.number_count;
        stats.total_number_value += node.get_number_value();
        break;

    default:
        assert(false && "unknown node type");
    }
}

int main(int argc, char** argv) {
    FILE* file = fopen(argv[1], "rb");
    if (!file) {
        fprintf(stderr, "Failed to open file\n");
        return 1;
    }
    fseek(file, 0, SEEK_END);
    size_t length = ftell(file);
    fseek(file, 0, SEEK_SET);

    // "leak"
    char* buffer = new char[length];
    if (length != fread(buffer, 1, length, file)) {
        fprintf(stderr, "Failed to read entire file\n");
        return 1;
    }
    fclose(file);

    const sajson::document& document = sajson::parse(
        sajson::dynamic_allocation(), mutable_string_view(length, buffer));
    if (!success(document)) {
        return 1;
    }

    jsonstats stats;
    traverse(stats, document.get_root());

    printf("object count: %d\n", (int)stats.object_count);
    printf("array count: %d\n", (int)stats.array_count);
    printf("bool count: %d\n", (int)stats.true_count + (int)stats.false_count);
    printf("number count: %d\n", (int)stats.number_count);
    printf("string count: %d\n", (int)stats.string_count);
    printf("null count: %d\n", (int)stats.null_count);
}
<commit_msg>Fix memory leaks<commit_after>#include "sajson.h"
#include <assert.h>

using namespace sajson;

inline bool success(const document& doc) {
    if (!doc.is_valid()) {
        fprintf(stderr, "%s\n", doc.get_error_message_as_cstring());
        return false;
    }
    return true;
}

struct jsonstats {
    jsonstats()
        : null_count(0)
        , false_count(0)
        , true_count(0)
        , number_count(0)
        , object_count(0)
        , array_count(0)
        , string_count(0)
        , total_string_length(0)
        , total_array_length(0)
        , total_object_length(0)
        , total_number_value(0) {}

    size_t null_count;
    size_t false_count;
    size_t true_count;
    size_t number_count;
    size_t object_count;
    size_t array_count;
    size_t string_count;

    size_t total_string_length;
    size_t total_array_length;
    size_t total_object_length;
    double total_number_value;
};

void traverse(jsonstats& stats, const sajson::value& node) {
    using namespace sajson;

    switch (node.get_type()) {
    case TYPE_NULL:
        ++stats.null_count;
        break;

    case TYPE_FALSE:
        ++stats.false_count;
        break;

    case TYPE_TRUE:
        ++stats.true_count;
        break;

    case TYPE_ARRAY: {
        ++stats.array_count;
        auto length = node.get_length();
        stats.total_array_length += length;
        for (size_t i = 0; i < length; ++i) {
            traverse(stats, node.get_array_element(i));
        }
        break;
    }

    case TYPE_OBJECT: {
        ++stats.object_count;
        auto length = node.get_length();
        stats.total_object_length += length;
        for (auto i = 0u; i < length; ++i) {
            traverse(stats, node.get_object_value(i));
        }
        break;
    }

    case TYPE_STRING:
        ++stats.string_count;
        stats.total_string_length += node.get_string_length();
        break;

    case TYPE_DOUBLE:
    case TYPE_INTEGER:
        ++stats.number_count;
        stats.total_number_value += node.get_number_value();
        break;

    default:
        assert(false && "unknown node type");
    }
}

int main(int argc, char** argv) {
    FILE* file = fopen(argv[1], "rb");
    if (!file) {
        fprintf(stderr, "Failed to open file\n");
        return 1;
    }
    fseek(file, 0, SEEK_END);
    size_t length = ftell(file);
    fseek(file, 0, SEEK_SET);

    char* buffer = new char[length];
    if (length != fread(buffer, 1, length, file)) {
        fclose(file);
        delete[] buffer;
        fprintf(stderr, "Failed to read entire file\n");
        return 1;
    }
    fclose(file);

    const sajson::document& document = sajson::parse(
        sajson::dynamic_allocation(), mutable_string_view(length, buffer));
    if (!success(document)) {
        fclose(file);
        delete[] buffer;
        return 1;
    }

    jsonstats stats;
    traverse(stats, document.get_root());

    printf("object count: %d\n", (int)stats.object_count);
    printf("array count: %d\n", (int)stats.array_count);
    printf("bool count: %d\n", (int)stats.true_count + (int)stats.false_count);
    printf("number count: %d\n", (int)stats.number_count);
    printf("string count: %d\n", (int)stats.string_count);
    printf("null count: %d\n", (int)stats.null_count);

    fclose(file);
    delete[] buffer;
    return 0;
}
<|endoftext|>


<commit_before>// Copyright (c) 2006-2008 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 "base/file_util.h"
#include "base/path_service.h"
#include "base/perftimer.h"
#include "base/time.h"
#include "chrome/app/chrome_dll_resource.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/test/automation/browser_proxy.h"
#include "chrome/test/ui/ui_test.h"
#include "net/base/net_util.h"

using base::TimeDelta;

namespace {

// Returns the directory name where the "typical" user data is that we use for
// testing.
FilePath ComputeTypicalUserDataSource() {
  FilePath source_history_file;
  EXPECT_TRUE(PathService::Get(chrome::DIR_TEST_DATA,
                               &source_history_file));
  source_history_file = source_history_file.AppendASCII("profiles")
      .AppendASCII("typical_history");
  return source_history_file;
}

class NewTabUIStartupTest : public UITest {
 public:
  NewTabUIStartupTest() {
    show_window_ = true;
  }

  void SetUp() {}
  void TearDown() {}

  static const int kNumCycles = 5;

  void PrintTimings(const char* label, TimeDelta timings[kNumCycles],
                    bool important) {
    std::string times;
    for (int i = 0; i < kNumCycles; ++i)
      StringAppendF(&times, "%.2f,", timings[i].InMillisecondsF());
    PrintResultList("new_tab", "", label, times, "ms", important);
  }

  // Run the test, by bringing up a browser and timing the new tab startup.
  // |want_warm| is true if we should output warm-disk timings, false if
  // we should report cold timings.
  void RunStartupTest(const char* label, bool want_warm, bool important) {
    // Install the location of the test profile file.
    set_template_user_data(ComputeTypicalUserDataSource().ToWStringHack());

    TimeDelta timings[kNumCycles];
    for (int i = 0; i < kNumCycles; ++i) {
      UITest::SetUp();

      // Switch to the "new tab" tab, which should be any new tab after the
      // first (the first is about:blank).
      BrowserProxy* window = automation()->GetBrowserWindow(0);
      ASSERT_TRUE(window);
      int tab_count = -1;
      ASSERT_TRUE(window->GetTabCount(&tab_count));
      ASSERT_EQ(1, tab_count);

      // Hit ctl-t and wait for the tab to load.
      window->ApplyAccelerator(IDC_NEW_TAB);
      ASSERT_TRUE(window->WaitForTabCountToBecome(2, 5000));
      int load_time;
      ASSERT_TRUE(automation()->WaitForInitialNewTabUILoad(&load_time));
      timings[i] = TimeDelta::FromMilliseconds(load_time);

      if (want_warm) {
        // Bring up a second tab, now that we've already shown one tab.
        window->ApplyAccelerator(IDC_NEW_TAB);
        ASSERT_TRUE(window->WaitForTabCountToBecome(3, 5000));
        ASSERT_TRUE(automation()->WaitForInitialNewTabUILoad(&load_time));
        timings[i] = TimeDelta::FromMilliseconds(load_time);
      }

      delete window;
      UITest::TearDown();
    }

    PrintTimings(label, timings, important);
  }
};

// TODO(pamg): run these tests with a reference build?
TEST_F(NewTabUIStartupTest, PerfCold) {
  RunStartupTest("tab_cold", false /* not cold */, true /* important */);
}

TEST_F(NewTabUIStartupTest, DISABLED_PerfWarm) {
  RunStartupTest("tab_warm", true /* cold */, false /* not important */);
}

}  // namespace
<commit_msg>Fix errant comments on parameters. BUG=none TEST=none Review URL: http://codereview.chromium.org/112062<commit_after>// Copyright (c) 2006-2008 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 "base/file_util.h"
#include "base/path_service.h"
#include "base/perftimer.h"
#include "base/time.h"
#include "chrome/app/chrome_dll_resource.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/test/automation/browser_proxy.h"
#include "chrome/test/ui/ui_test.h"
#include "net/base/net_util.h"

using base::TimeDelta;

namespace {

// Returns the directory name where the "typical" user data is that we use for
// testing.
FilePath ComputeTypicalUserDataSource() {
  FilePath source_history_file;
  EXPECT_TRUE(PathService::Get(chrome::DIR_TEST_DATA,
                               &source_history_file));
  source_history_file = source_history_file.AppendASCII("profiles")
      .AppendASCII("typical_history");
  return source_history_file;
}

class NewTabUIStartupTest : public UITest {
 public:
  NewTabUIStartupTest() {
    show_window_ = true;
  }

  void SetUp() {}
  void TearDown() {}

  static const int kNumCycles = 5;

  void PrintTimings(const char* label, TimeDelta timings[kNumCycles],
                    bool important) {
    std::string times;
    for (int i = 0; i < kNumCycles; ++i)
      StringAppendF(&times, "%.2f,", timings[i].InMillisecondsF());
    PrintResultList("new_tab", "", label, times, "ms", important);
  }

  // Run the test, by bringing up a browser and timing the new tab startup.
  // |want_warm| is true if we should output warm-disk timings, false if
  // we should report cold timings.
  void RunStartupTest(const char* label, bool want_warm, bool important) {
    // Install the location of the test profile file.
    set_template_user_data(ComputeTypicalUserDataSource().ToWStringHack());

    TimeDelta timings[kNumCycles];
    for (int i = 0; i < kNumCycles; ++i) {
      UITest::SetUp();

      // Switch to the "new tab" tab, which should be any new tab after the
      // first (the first is about:blank).
      BrowserProxy* window = automation()->GetBrowserWindow(0);
      ASSERT_TRUE(window);
      int tab_count = -1;
      ASSERT_TRUE(window->GetTabCount(&tab_count));
      ASSERT_EQ(1, tab_count);

      // Hit ctl-t and wait for the tab to load.
      window->ApplyAccelerator(IDC_NEW_TAB);
      ASSERT_TRUE(window->WaitForTabCountToBecome(2, 5000));
      int load_time;
      ASSERT_TRUE(automation()->WaitForInitialNewTabUILoad(&load_time));
      timings[i] = TimeDelta::FromMilliseconds(load_time);

      if (want_warm) {
        // Bring up a second tab, now that we've already shown one tab.
        window->ApplyAccelerator(IDC_NEW_TAB);
        ASSERT_TRUE(window->WaitForTabCountToBecome(3, 5000));
        ASSERT_TRUE(automation()->WaitForInitialNewTabUILoad(&load_time));
        timings[i] = TimeDelta::FromMilliseconds(load_time);
      }

      delete window;
      UITest::TearDown();
    }

    PrintTimings(label, timings, important);
  }
};

// TODO(pamg): run these tests with a reference build?
TEST_F(NewTabUIStartupTest, PerfCold) {
  RunStartupTest("tab_cold", false /* cold */, true /* important */);
}

TEST_F(NewTabUIStartupTest, DISABLED_PerfWarm) {
  RunStartupTest("tab_warm", true /* warm */, false /* not important */);
}

}  // namespace
<|endoftext|>


<commit_before>#include <unistd.h>
#include <cstring>
#include <fstream>
#include <linux/limits.h>

#include "Macros.h"
#include "Environment.h"

namespace magpie
{
  gc<String> getCoreLibDir()
  {
    char* relativePath[PATH_MAX];

    int len = readlink("/proc/self/exe", relativePath, PATH_MAX - 1);
    ASSERT(len != -1, "Executable path too long.");
    relativePath[len] = '\0';

    // Cut off file name from path
    char* lastSep = NULL;
    for (char* c = relativePath; *c != '\0'; c++)
    {
      if (*c == '/')
      {
        lastSep = c;
      }
    }

    if (lastSep != NULL)
    {
      *lastSep = '\0';
    }

    // Find the magpie main directory relative to the executable.
    // TODO(bob): Hack. Try to work from the build directory too.
    if (strstr(relativePath, "1/out") != 0)
    {
      strncat(relativePath, "/../../..", PATH_MAX);
    }

    // Add core library directory.
    strncat(relativePath, "/core", PATH_MAX);

    // Canonicalize the path.
    char path[PATH_MAX];
    realpath(relativePath, path);
    return String::create(path);
  }

  // Reads a file from the given path into a String.
  gc<String> readFile(gc<String> path)
  {
    // TODO(bob): Use platform-native API for this?
    using namespace std;

    ifstream stream(path->cString());

    if (stream.fail()) return gc<String>();

    // From: http://stackoverflow.com/questions/2602013/read-whole-ascii-file-into-c-stdstring.
    string str;

    // Allocate a std::string big enough for the file.
    stream.seekg(0, ios::end);
    str.reserve(stream.tellg());
    stream.seekg(0, ios::beg);

    // Read it in.
    str.assign((istreambuf_iterator<char>(stream)),
               istreambuf_iterator<char>());

    return String::create(str.c_str());
  }
}<commit_msg>fix pointer type<commit_after>#include <unistd.h>
#include <cstring>
#include <fstream>
#include <linux/limits.h>

#include "Macros.h"
#include "Environment.h"

namespace magpie
{
  gc<String> getCoreLibDir()
  {
    char relativePath[PATH_MAX];

    int len = readlink("/proc/self/exe", relativePath, PATH_MAX - 1);
    ASSERT(len != -1, "Executable path too long.");
    relativePath[len] = '\0';

    // Cut off file name from path
    char* lastSep = NULL;
    for (char* c = relativePath; *c != '\0'; c++)
    {
      if (*c == '/')
      {
        lastSep = c;
      }
    }

    if (lastSep != NULL)
    {
      *lastSep = '\0';
    }

    // Find the magpie main directory relative to the executable.
    // TODO(bob): Hack. Try to work from the build directory too.
    if (strstr(relativePath, "1/out") != 0)
    {
      strncat(relativePath, "/../../..", PATH_MAX);
    }

    // Add core library directory.
    strncat(relativePath, "/core", PATH_MAX);

    // Canonicalize the path.
    char path[PATH_MAX];
    realpath(relativePath, path);
    return String::create(path);
  }

  // Reads a file from the given path into a String.
  gc<String> readFile(gc<String> path)
  {
    // TODO(bob): Use platform-native API for this?
    using namespace std;

    ifstream stream(path->cString());

    if (stream.fail()) return gc<String>();

    // From: http://stackoverflow.com/questions/2602013/read-whole-ascii-file-into-c-stdstring.
    string str;

    // Allocate a std::string big enough for the file.
    stream.seekg(0, ios::end);
    str.reserve(stream.tellg());
    stream.seekg(0, ios::beg);

    // Read it in.
    str.assign((istreambuf_iterator<char>(stream)),
               istreambuf_iterator<char>());

    return String::create(str.c_str());
  }
}
<|endoftext|>


<commit_before><commit_msg>fix type error build error in android react native<commit_after><|endoftext|>