
/*
 *      Copyright (c) 2023, an unpublished work by CodeSecure, Inc.
 *                      ALL RIGHTS RESERVED
 *
 *      Copyright (c) 2014-2023, an unpublished work by GrammaTech, Inc.
 *                      ALL RIGHTS RESERVED
 *
 *      This software is furnished under a license and may be used and
 *      copied only in accordance with the terms of such license and the       
 *      inclusion of the above copyright notice.  This software or any
 *      other copies thereof may not be provided or otherwise made
 *      available to any other person.  Title to and ownership of the
 *      software is retained by CodeSecure, Inc.
 */

/* iolibrary.c
 *
 * Contains definitions for iolibrary.
 */

#include <string.h>
#include "iolibrary.h"

/* Open the file named fname.
 * Return a pointer to the opened file.
 */
FILE * open_a_file(char *fname){ 
  return fopen(fname, "a+");
}


/* Close the specified file. 
 * Return 1 on success, 0 on failure.
 */ 
int close_a_file(FILE* f){ 
  return fclose(f);
}


/* Read up to numchars-1 charaters from the file specified by src 
 * into the buffer specified by dest. 
 * Return dest on success, NULL on failure. 
 */
char * read_string_from_file(char *dest, size_t numchars, FILE *src){
  return fgets(dest, numchars, src);
}


/* Write a  string from the buffer specified by src 
 * into the file specified by dest. 
 * Return non-negative integer on success, EOF on failure. 
 */
int write_string_to_file(char *src, FILE *dest){
  return fputs(src, dest);
}


/* Return the number of characters required to store the sanitized
 * version of 'raw'. The sanitized version of a string is always at 
 * least as long as the raw version.
 * Return -1 if the number of characters required
 * would exceed the largest value expressible as a size_t.
 */
int sanitized_size(char *raw){
  size_t i;
  size_t slashcount = 0;
  size_t len = strlen(raw);

  for (i = 0; i < len; i++){
    if (raw[i] == '/'){ slashcount++;}
  }
  if (len >  len + slashcount) {return -1;} 
  return len + slashcount;
}

/* Generate a version of 'raw' that contains no elements that could be
 * dangerous in a call to print_important_data(), and store it in
 * 'sanitized'. The sanitized string is guaranteed to be safe to use
 * with print_important_data().
 *
 * Important: this is NOT a general-purpose string sanitizing function. 
 *
 * Return 1 on success, 0 on failure.
 */
int sanitize_file_string(char *raw, char *sanitized){
  int r_marker;
  int s_marker;
  char rchar;
  
  /* Failure cases. */
  if (sanitized_size(raw) == -1) {return 0;}
  if (strlen(raw) == 0) {return 0;}

  s_marker = 0;
  for (r_marker = 0; r_marker <strlen(raw); r_marker++){
    rchar = raw[r_marker];
    if (rchar == '/'){
      sanitized[s_marker++] = '\\';  
    }
    sanitized[s_marker++] = raw[r_marker];
  }
  return 1;
}


/* Prints a piece of important data to stdout, using 'str' to
 * determine which piece of data to print. This could cause security
 * problems if 'str' is tainted'.
 * Return 1 on success, 0 on failure.
 */
int print_important_data(char *str){
  printf("Data: %s", str);
  return 1;
}
