blob: 747b8777253452d5454dc3df13c07da737ff6c2a [file] [log] [blame]
//-------------------------------------------------------------------------
//
// @@@ START COPYRIGHT @@@
//
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License.
//
// @@@ END COPYRIGHT @@@
//
// (06/24/2013)
// This program is not a participant in general Linux SQL build, unless env
// SQ_COVERAGE or SQ_COVERAGE_OPTIMIZER is specified, see
// nskgmake/Makerules.linux. To build it by default, add "memtest" to the
// EXECUTABLE list iin Makerules.linux.
// Once built, it can be run standalone. However, it would also be invoked
// by regress/core/TESTMEM and increase the regression runtime substantially.
//
//-------------------------------------------------------------------------
#include "NAMemory.h"
#include <fstream>
#include <unistd.h>
#include <ios>
#include <iostream>
#include <string>
#include <math.h>
#include <stdlib.h>
#include <sys/time.h>
typedef void* voidPtr;
void memtest_vers2_print() {};
#include "seabed/ms.h"
#include "seabed/fs.h"
extern void my_mpi_fclose();
#include "SCMVersHelp.h"
DEFINE_DOVERS(memtest)
extern "C"
{
Int32 sq_fs_dllmain();
}
void process_mem_usage(long& vm_usage, long& resident_set)
{
using std::ios_base;
using std::ifstream;
using std::string;
vm_usage = 0.0;
resident_set = 0.0;
// dummy vars for leading entries in stat that we don't care about
//
string pid, comm, state, ppid, pgrp, session, tty_nr;
string tpgid, flags, minflt, cminflt, majflt, cmajflt;
string utime, stime, cutime, cstime, priority, nice;
string O, itrealvalue, starttime;
// the two fields we want
//
unsigned long vsize;
long rss;
// 'file' stat seems to give the most reliable results
//
ifstream stat_stream("/proc/self/stat",ios_base::in);
stat_stream >> pid >> comm >> state >> ppid >> pgrp >> session >> tty_nr
>> tpgid >> flags >> minflt >> cminflt >> majflt >> cmajflt
>> utime >> stime >> cutime >> cstime >> priority >> nice
>> O >> itrealvalue >> starttime >> vsize >> rss;
// don't care about the rest
stat_stream.close();
long page_size_kb = sysconf(_SC_PAGE_SIZE) / 1024;
// in case x86-64 is configured to use 2MB pages
vm_usage = vsize / 1024;
resident_set = rss * page_size_kb;
}
int main(int argc, char** argv)
{
dovers(argc, argv);
try
{
file_init_attach(&argc, &argv, TRUE, (char *)"");
sq_fs_dllmain();
file_mon_process_startup(true);
msg_debug_hook("memtest", "memtest.hook");
atexit(my_mpi_fclose);
}
catch (...)
{
exit(1);
}
long vmSize, resSize;
timeval startTm, endTm;
int counts = 0;
int failedCnt = 0;
NASegGlobals segGlobals;
NAHeap hp("Simulated global exec memory", 0,0,0,0,0,&segGlobals, 28);
#define ONE_G (1024 * 1024 * 1024L)
#define MAX_ALLOCATES 200000
voidPtr hps[MAX_ALLOCATES];
process_mem_usage(vmSize, resSize);
printf("memtest: before testing: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
printf("memtest: phace I tests (random memory de/allocations):\n");
voidPtr x = hp.allocateHeapMemory(size_t(568041472), FALSE);
if (x != NULL)
{
process_mem_usage(vmSize, resSize);
printf("memtest: after 500MB alloc: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
hp.deallocateHeapMemory(x);
process_mem_usage(vmSize, resSize);
printf("memtest: after 500MB de-alloc: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
}
else
printf("memtest: failed to allocate a 500MB chunk!\n");
printf("memtest: continue random memory (de)allocation for size less than 1MB\n");
gettimeofday(&startTm, 0);
srand(time(NULL));
for ( int i=0; i<MAX_ALLOCATES; i++ ) {
int sz = rand() % 1000000;
hps[i] = hp.allocateHeapMemory(size_t(sz), FALSE);
if (hps[i] == NULL)
failedCnt++;
else if (sz > 500000)
counts++;
if ( rand() % 1 ) {
int index = rand() % i;
if ( hps[index] ) {
hp.deallocateHeapMemory(hps[index]);
hps[index] = NULL;
}
}
}
gettimeofday(&endTm, 0);
printf("\n");
printf("memtest: larger than 500KB: %d; failed %d\n", counts, failedCnt);
process_mem_usage(vmSize, resSize);
printf("memtest: before cleanup: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
printf("memtest: time spent for 200K allocations: %ld sec\n", (endTm.tv_sec - startTm.tv_sec));
for ( int i=0; i<MAX_ALLOCATES; i++ )
if ( hps[i] )
hp.deallocateHeapMemory(hps[i]);
gettimeofday(&endTm, 0);
hp.reInitialize();
printf("memtest: phase I tests spent: %ld sec\n", (endTm.tv_sec - startTm.tv_sec));
process_mem_usage(vmSize, resSize);
printf("memtest: after phase I cleanup: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
printf("memtest: phase II tests (aligned fragments (de)allocate):\n");
srand(time(NULL));
for ( int i=0; i<MAX_ALLOCATES; i++ ) {
int sz = 4096;
hps[i] = hp.allocateAlignedHeapMemory(size_t(sz), size_t(512), FALSE);
if ( rand() % 1 ) {
int index = rand() % i;
if ( hps[index] ) {
hp.deallocateHeapMemory(hps[index]);
hps[index] = NULL;
}
}
}
for ( int i=0; i<MAX_ALLOCATES; i++ )
if ( hps[i] )
hp.deallocateHeapMemory(hps[i]);
hp.reInitialize();
printf("memtest: phase II tests done.\n");
process_mem_usage(vmSize, resSize);
printf("memtest: after phase II cleanup: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
printf("memtest: phase III tests (larger than 2GB chunk (de)allocate):\n");
for ( int i=1; i<12; i++)
{
Int32 j = 1 << i;
printf("memtest: to allocate %d GB chunk...\n", j);
voidPtr z = hp.allocateHeapMemory(size_t(j * ONE_G), FALSE);
if (z != NULL) {
memcpy((char *)z, "beginning", (size_t)9);
memcpy(((char *)z + j * ONE_G - 6), "ending", (size_t)6);
}
else {
printf("memtest: failed to allocate a %d GB chunk!\n", j);
process_mem_usage(vmSize, resSize);
printf("memtest: current usage: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
break;
}
}
hp.reInitialize();
sleep(10);
process_mem_usage(vmSize, resSize);
printf("memtest: after all de-alloc: vmSize %ldKB resSize %ldKB\n",
vmSize, resSize);
printf("memtest: phase III tests done.\n");
return 0;
}