You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

193 lines
4.5 KiB

/*
* Copyright 2002-2019 Intel Corporation.
*
* This software is provided to you as Sample Source Code as defined in the accompanying
* End User License Agreement for the Intel(R) Software Development Products ("Agreement")
* section 1.L.
*
* This software and the related documents are provided as is, with no express or implied
* warranties, other than those that are expressly stated in the License.
*/
// test-mt3.cpp -- a simple multithreaded test program. I added markers to
// this to trigger the controller.
// g++ -o test-mt3 test-mt3.cpp -lpthread
////////////////////////////////////////////////////////////////////////////
#include <cassert>
#include <string>
#include <stdio.h>
#include <iostream>
#include <ostream>
#include <iomanip>
#include <cstdlib>
#include <cctype>
#include <mmintrin.h>
#include <emmintrin.h>
#include <xmmintrin.h>
#include<pthread.h>
using std::cout;
using std::endl;
////////////////////////////////////////////////////////////////////////////
// DEFINES
////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////
// TYPES
////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////
// PROTOTYPES
////////////////////////////////////////////////////////////////////////////
int main(int argc, char** argv, char** envp);
////////////////////////////////////////////////////////////////////////////
// GLOBALS
////////////////////////////////////////////////////////////////////////////
extern "C" {
// These functions are markers. The symbols are used to control tracing.
void marker_start_counting()
{
asm volatile(".byte 0xbb,0x11,0x22,0x33,0x44,0x64,0x67,0x90" : : : "ebx");
}
void marker_stop_counting()
{
asm volatile(".byte 0xbb,0x11,0x22,0x33,0x55,0x64,0x67,0x90" : : : "ebx");
}
void marker_emit_stats()
{
}
void marker_zero_stats()
{
}
}
class THREAD_STATE_T
{
public:
int x;
THREAD_STATE_T() {
}
};
pthread_mutex_t my_mutex;
extern "C" void work1() {
int i;
float x,y,z;
__m128 m1 = _mm_load_ss(&x);
__m128 m2 = _mm_load_ss(&y);
__m128 sum = _mm_add_ss(m1,m2);
for(i=0;i<50;i++) {
__m128 sum = _mm_add_ss(m1,m2);
}
_mm_store_ss(&z, sum);
}
extern "C" void work2() {
int i;
float x,y,z;
__m128 m1 = _mm_load_ss(&x);
__m128 m2 = _mm_load_ss(&y);
__m128 sum = _mm_add_ss(m1,m2);
for(i=0;i<50;i++) {
__m128 sum = _mm_sub_ss(m1,m2);
}
_mm_store_ss(&z, sum);
}
extern "C" void work3() {
int i;
float x,y,z;
__m128 m1 = _mm_load_ss(&x);
__m128 m2 = _mm_load_ss(&y);
__m128 sum = _mm_add_ss(m1,m2);
for(i=0;i<50;i++) {
__m128 sum = _mm_mul_ss(m1,m2);
}
_mm_store_ss(&z, sum);
}
extern "C" void work4() {
int i;
float x=3,y=1,z=2;
__m128 m1 = _mm_load_ss(&x);
__m128 m2 = _mm_load_ss(&y);
__m128 sum = _mm_add_ss(m1,m2);
for(i=0;i<50;i++) {
__m128 sum = _mm_div_ss(m1,m2);
}
_mm_store_ss(&z, sum);
}
static void (*work[4])() = {
work1, work2, work3, work4
};
void*
start_routine(void* arg)
{
marker_zero_stats();
marker_start_counting();
THREAD_STATE_T* thread_state = (THREAD_STATE_T*) arg;
marker_emit_stats();
for(unsigned int i=0;i<50; i++)
{
marker_zero_stats();
marker_start_counting();
(*work[thread_state->x%4])();
marker_stop_counting();
marker_emit_stats();
}
return 0;
}
int main(int argc, char** argv, char** envp)
{
pthread_attr_t attr;
int nthreads = (argc==2) ? atoi(argv[1]) : 4;
THREAD_STATE_T* thread_state = new THREAD_STATE_T[nthreads];
pthread_t* thread = new pthread_t[nthreads];
int r;
r = pthread_mutex_init(&my_mutex, 0);
assert(r==0);
r = pthread_attr_init(&attr);
assert(r==0);
for(int i=0;i<nthreads;i++)
{
thread_state[i].x = i;
r = pthread_create( thread+i,
&attr,
start_routine,
(void*) (thread_state+i) );
assert(r==0);
}
r = pthread_mutex_lock(&my_mutex);
assert(r==0);
cout << "I'm in the main thread!" << endl;
r = pthread_mutex_unlock(&my_mutex);
assert(r==0);
for(int i=0;i<nthreads;i++) {
r = pthread_join(thread[i], 0);
assert(r==0);
}
return 0;
}
////////////////////////////////////////////////////////////////////////////