/*
    Living Realms is a primate evolution simulator.
    Copyright (C) 2011  Sterling Pickens

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program 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 General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.
*/

#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <sys/types.h>


int main(int argc, char **argv){
	char *in_name = (char *)malloc(strlen("../gebco_08.nc") + 1);
    strcpy(in_name, "../gebco_08.nc");
	char *out_name = (char *)malloc(strlen("myout.test") + 1);
    strcpy(out_name, "myout.test");
	union{ char a[2]; int16_t b;}x;
	

    FILE *input = fopen(in_name, "rb");
	FILE *output = fopen(out_name, "wb");
    if(!input){
        printf("Error opening file: %s\n", in_name);
        return 1;
    }
	if(!output){
		printf("Error opening file: %s\n", out_name);
		return 1;
	}

	double sum = 0;
	int temp_num = 0;
	unsigned int count1 = 0;
	unsigned int count2 = 0;
	unsigned int count3 = 0;
	unsigned int count4 = 0;
	unsigned int count5 = 0;
	unsigned int count6 = 0;

	//1866240612
	unsigned int in_rows = 21600;
	unsigned int in_cols = 43200;
	unsigned int out_rows = in_rows/12;
	unsigned int out_cols = in_cols/12;


	size_t in_bytes  = sizeof(char)*12*in_cols*2;
	size_t out_bytes = sizeof(char)*out_cols*2;

	//char *in_temp = malloc(in_bytes);
	//char *out_temp = malloc(out_bytes);

	//int16_t test_in[in_rows][in_cols];
	//int16_t test_out[out_rows][out_cols];

	int16_t **test_in = (int16_t **)malloc(sizeof(int16_t *) *in_rows);
	for(count1=0; count1<in_rows; count1++)
		test_in[count1] = (int16_t *)malloc(sizeof(int16_t) *in_cols);
	int16_t **test_out = (int16_t **)malloc(sizeof(int16_t *) *out_rows);
	for(count1=0; count1<out_rows; count1++)
		test_out[count1] = (int16_t *)malloc(sizeof(int16_t) *out_cols);

	printf("in:\n");
	printf("buffer: %zu\n", in_bytes);
	printf("\tX: %u\n", in_cols);
	printf("\tY: %u\n", in_rows);
	printf("out:\n");
	printf("buffer: %zu\n", out_bytes);
	printf("\tX: %u\n", out_cols);
	printf("\tY: %u\n", out_rows);



	//1800 3600
	//21600 rows 43200 cols
	//read 12 rows at a time
	//averages of 12x12 regions = new data point
printf("here 1\n");
	char twoc[2];
	size_t bytes_read = 0;
	size_t bytes_wrote = 0;

	fseek ( input , 612 , SEEK_SET );

	for(count1=0; count1<in_rows; count1++){
		for(count2=0; count2<in_cols; count2++){
			bytes_read += fread((void *)&twoc, 1, 2, input);
				//printf("failed to read
			x.a[0] = twoc[1];
			x.a[1] = twoc[0];
			
			test_in[count1][count2]=x.b;
		}
	}
	fclose(input);
/*
//	char twoc[2];
	for(count1=0; count1<in_rows; count1++){
		for(count2=0; count2<in_cols; count2++){
			x.b = test_in[count1][count2];
			twoc[0] = x.a[1];
			twoc[1] = x.a[0];
			bytes_wrote += fwrite((const void *)&twoc, 1, 2, output);
		}
	}
	
	printf("read: %zu wrote %zu\n", bytes_read, bytes_wrote);
	//fwrite((const void *)&test_in, 2, in_rows*in_cols, output);
	
*/


printf("here 2\n");
	double twelve[out_cols];
	(void)memset(&twelve, 0, out_cols*sizeof(double) );
printf("here 3\n");
	//for(count1=0; count1<out_rows; count1++){
	//	for(count2=0; count2<out_cols; count2++){
	//		for(count1=0; count1<in_rows; count1++){
	//			for(count2=0; count2<12; count2++){
	count4 = 0;
	count5 = 0;
	for(count1=0; count1<in_rows; count1++){
		//(void)memset(&twelve, '\0', out_cols*sizeof(double) );
		//count6 = 0;
		//count3=11;
		//for(count2=0; count2<in_cols; count2++){
		//	count3++;
		//	if(count3 == 12){
		//		twelve[count6] = (double)test_in[count1][count2];
		//		count3=0;
		//		count6++;
		//	}
		//}
		for(count2=0; count2<out_cols; count2++){
			for(count3=0; count3<12; count3++){
				twelve[count2] += (double)test_in[count1][count2*12+count3];
			}
		}
		count4++;
		if(count4 == 12){ //have the sum of 12 input rows
			//for(count5=0; count5<in_rows; count5++){
				for(count6=0; count6<out_cols; count6++){
					//sum = twelve[count6]/144;
					test_out[count5][count6] = (int16_t)ceil(twelve[count6]/144);
				}
			count5++;
			count4=0;
			(void)memset(&twelve, 0, out_cols*sizeof(double) );
		}
	}
	for(count1=0; count1<out_rows; count1++){
		for(count2=0; count2<out_cols; count2++){
			fwrite((const void *)&test_out[count1][count2], 1, 2, output);
		}
	}

	//	sum += test_in[count1][count2];
	//	if(count2 % 12){
	//		twelve[out_cols] = sum;
	//	}
	//	count2++;
	//	if(count1 % 12){
	//		test_out[out_rows][out_cols] = (int16_t)ceil(sum/144);

	/*
	for(count1=0; count1<out_rows; count1++){
		fread((void *)in_temp, in_bytes, 1, input);

		for(count2=0; count2<out_cols; count2++){
			//fread((void *)&in_temp, 1, in_bytes, input);
			for(count3=0; count3<12; count3++){
				for(count4=0; count4<12; count4++){
					
					x.a[1] = in_temp[(in_cols*count3+count4)*2];
					x.a[0] = in_temp[(in_cols*count3+count4)*2+1];
					sum += x.b;
				}
			}
			//msb to lsb
			temp_num = ceil(sum/144);

			//test_out[count2] = (int16_t)temp_num;
			x.b = (int16_t)temp_num;
			if(x.b > 9500 || x.b < -13500){
				printf("%d\n", x.b);
			}
			out_temp[count2*2]   = x.a[1];
			out_temp[count2*2+1] = x.a[0];
			sum = 0;
		}
		//printf("here 1\n");
		fwrite((const void *)&out_temp[0], out_cols*2, 1, output);
	}
	*/


	//fclose(input);
	fclose(output);
	free(in_name);
	free(out_name);
	free(test_in);
	free(test_out);
	//free(in_temp);
	//free(out_temp);
	printf("finished!\n");

	return 0;
}