What do the various portions of a compiler returned error mean? - error-handling

The question is pretty basic.
Code:
#include<iostream>
#include<fstream>
using namespace std;
struct Customer
{
char name[20];
char cell[12];
double bal;
};
int get_total_records_from_file(char * filename)
{
// Implement this funtion
return 0;
}
void get_input_from_user(Customer * ptr){
cin.ignore();
for(int i = 0; i < customer_count; i++){
cout<<"Enter Customer Name (1-20 character long)"<<endl;
cin.getline(ptr[i].name,20);
cout<<"Enter Cell No. (11 character long)"<<endl;
cin.getline(ptr[i].cell,20);
cout<<"Enter Initial Balance"<<endl;
cin >> ptr[i].bal;
cin.ignore();
}
}
If I have this error:
main.cpp:22:21: error: ‘customer_count’ was not declared in this scope
what do the various portions of it mean? That is, what's 22? what's 21? etcetra.

Related

Initialize C++/CLI array of structures

I wish to partially initialize an array of structures like in a C++ POD type. The String^ would normally be a char* but managed C++ doesn't allow that.
#include "stdafx.h"
using namespace System;
ref struct Field
{
String^ name;
int fences;
int length;
};
int main(array<System::String ^> ^args)
{
array<Field^>^ farm =
{
{ "eenie", 10 },
{ "meenie", 20 },
{ "miny", 4 }
};
for each (Field^ field in farm)
{
field->length = field->fences * 22;
}
return 0;
}
This results in
1>arrayinit.cpp(18): error C2440: 'initializing' : cannot convert from 'const char [6]' to 'Field ^'
1> Reason: cannot convert from 'const char *' to 'Field ^'
1> No user-defined-conversion operator available, or
1> Cannot convert an unmanaged type to a managed type
So I tried
#include "stdafx.h"
using namespace System;
ref struct Field
{
String^ name;
int fences;
int length;
};
int main(array<System::String ^> ^args)
{
array<Field^>^ farm =
{
{ String("eenie"), 10 },
{ String("meenie"), 20 },
{ String("miny"), 4 }
};
for each (Field^ field in farm)
{
field->length = field->fences * 22;
}
return 0;
}
Now I get
1>arrayinit.cpp(18): error C2440: 'initializing' : cannot convert from 'System::String' to 'Field ^'
1> No user-defined-conversion operator available, or
1> No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called
1>arrayinit.cpp(18): error C2078: too many initializers
Almost every example I've looked at only tells how to initialize an array of strings or integers. I haven't found out a way of initializing an array of structures containing strings.
Is there a simple way of doing this or do I have to create a special constructor and gcnew every element?
I found that I can gcnew every element with a special constructor. Is there a simpler way of doing this similar to a POD initialization?
#include "stdafx.h"
using namespace System;
ref struct Field
{
String^ name;
int fences;
int length;
Field(String^ x, int in_fences)
{
name = x;
fences = in_fences;
}
};
int main(array<System::String ^> ^args)
{
array<Field^>^ farm =
{
gcnew Field("eenie", 10 ),
gcnew Field("meenie", 20 ),
gcnew Field("miny", 4 )
};
for each (Field^ field in farm)
{
field->length = field->fences * 22;
}
return 0;
}
Alternatively, if Field is changed to a value instead of a reference,
#include "stdafx.h"
using namespace System;
value struct Field
{
String^ name;
int fences;
int length;
Field(String^ x, int in_fences)
{
name = x;
fences = in_fences;
}
void Init()
{
length = fences * 22;
}
};
int main(array<System::String ^> ^args)
{
array<Field>^ farm =
{
Field("eenie", 10 ),
Field("meenie", 20 ),
Field("miny", 4 )
};
for each (Field% field in farm)
{
field.Init();
}
return 0;
}
This is slightly better than gcnewing every field.

Infinite printing on read command of character device (through cat command) [duplicate]

I am working on simple character device driver. I have implemented read and write functions in the module, the problem is when I try to read the device file using cat /dev/devicefile it is going into infinite loop i.e. reading the same data repeatedly. Can someone suggest me any solution to this problem? Below is my driver code.
#include<linux/module.h>
#include<linux/fs.h>
#include<linux/string.h>
#include<asm/uaccess.h>
#include<linux/init.h>
MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("character device driver");
MODULE_AUTHOR("Srinivas");
static char msg[100]={0};
static int t;
static int dev_open(struct inode *, struct file *);
static int dev_rls(struct inode *, struct file *);
static ssize_t dev_read(struct file *, char *,size_t, loff_t *);
static ssize_t dev_write(struct file *, const char *, size_t,loff_t *);
static struct file_operations fops =
{
.read = dev_read,
.open = dev_open,
.write = dev_write,
.release = dev_rls,
};
static int himodule( void )
{
t = 0;
t = register_chrdev(0, "chardevdriver", &fops);
if (t < 0)
printk(KERN_ALERT"device registration failed\n");
else
printk(KERN_ALERT"device registered successfully\n");
printk(KERN_ALERT"major number is %d", t);
return 0;
}
static void byemodule(void)
{
unregister_chrdev(t, "chardevdriver");
printk(KERN_ALERT"successfully unregistered\n");
}
static int dev_open(struct inode *inod, struct file *fil)
{
printk(KERN_ALERT"inside the dev open");
return 0;
}
static ssize_t dev_read(struct file *filp, char *buff, size_t len, loff_t *off)
{
short count = 0;
while (msg[count] != 0) {
put_user(msg[count], buff++);
count++;
}
return count;
}
static ssize_t dev_write(struct file *filp, const char *buff, size_t len, loff_t *off)
{
short count = 0;
printk(KERN_ALERT"inside write\n");
memset(msg,0,100);
printk(KERN_ALERT" size of len is %zd",len);
while (len > 0) {
msg[count] = buff[count];
len--;
count++;
}
return count;
}
static int dev_rls(struct inode *inod,struct file *fil)
{
printk(KERN_ALERT"device closed\n");
return 0;
}
module_init(himodule);
module_exit(byemodule);
.read function should also correctly process its len and off arguments. The simplest way to implement reading from memory-buffered file is to use simple_read_from_buffer helper:
static ssize_t dev_read(struct file *filp, char *buff, size_t len, loff_t *off)
{
return simple_read_from_buffer(buff, len, off, msg, 100);
}
You can inspect code of that helper (defined in fs/libfs.c) for educational purposes.
BTW, for your .write method you could use simple_write_to_buffer helper.
You are not respecting the buffer size passed into the dev_read function, so you may be invoking undefined behaviour in cat. Try this:
static ssize_t dev_read( struct file *filp, char *buff, size_t len, loff_t *off )
{
size_t count = 0;
printk( KERN_ALERT"inside read %d\n", *off );
while( msg[count] != 0 && count < len )
{
put_user( msg[count], buff++ );
count++;
}
return count;
}
This problem can be solved by correctly setting *off (fourth parameter of my_read()).
You need to return count for the first time and zero from second time onwards.
if(*off == 0) {
while (msg[count] != 0) {
put_user(msg[count], buff++);
count++;
(*off)++;
}
return count;
}
else
return 0;

Convert decimal to binary and return array

probably there is a smart way to do that , but anyway i get error on this :
-(int*)decimalBinary:(int)decimal
{
int i=0;
int *bin;
while (decimal!=0)
{
bin[i]=decimal%2;
decimal=decimal/2;
i++;
}
return bin;
}
on the modulo line . why ?
And whats the better way to get it to array ?
Declaring
int *bin;
sets aside space for a pointer but doesn't make it point to an object. It is crucial to initialize bin before using it.
To solve your problem you can declare an array bin[4] in caller function (int main) and then pass *bin to your calling function.
The following code is adapted from This answer on how to print an integer in binary format. Storing "binary digits" into an int array is added into the code below:
#include <stdio.h> /* printf */
#include <stdlib.h> /* strtol */
const char *byte_to_binary(long x);
int main(void)
{
long lVal;
int i, len, array[18];
char buf[18];
{ /* binary string to int */
char *tmp;
char *b = "11010111001010110";
lVal=strtol(b, &tmp, 2); //convert string in "base 2" format to long int
printf("%d\n", lVal);
}
{
printf("%s", byte_to_binary(lVal));
/* byte to binary string */
sprintf(buf,"%s", byte_to_binary(lVal));
}
len = strlen(buf);
for(i=0;i<len;i++)
{ //store binary digits into an array.
array[i] = (buf[i]-'0');
}
getchar();
return 0;
}
const char *byte_to_binary(long x)
{
static char b[17]; //16 bits plus '\0'
b[0] = '\0';
char *p = b;
int z;
for (z = 65536; z > 0; z >>= 1) //2^16
{
*p++ = (x & z) ? '1' : '0';
}
return b;
}

Gets related problem

#include <stdio.h>
int main ()
{
FILE * pFile;
int n;
char name [100];
pFile = fopen ("myfile.txt", "w");
for (n = 0; n < 3; n++)
{
puts ("please, enter a name: ");
gets (name);
fprintf (pFile, "Name %d [%-10.10s]\n", n, name);
}
fclose (pFile);
return 0;
}
this code gives me a warning in gcc saying 'gets is a dangerous function to use'...is there a workaround for it?
Yes it is fgets. Replace your call to gets with:
fgets(name, 100, stdin)
For more details see the docs - the two are not exactly the same.

variable argument function

while doing a program related to variable argument function i
got the header file stdarg.h and have done some simple problem using it
but now when i a changing the actual argument's type it is showing some weird behaviour
here is my code:
#include<stdio.h>
#include<stdarg.h>
void fun(int a,...)
{
va_list k;
va_start(k,a);
int i=0;
printf("%d ",a);
while((i=va_arg(k,int)!=0)
{
printf(" %d ",i);
}
va_end(k);
}
int main()
{
fun(1,2,3,4,5,6);
printf("\n");
fflush(); //and without flush it is also showing some extra garbage value
fun(2,4,5);
printf("\n");
fflush();
fun('c','f','g','l');
return 0;
}
If you use the integer value 0 to indicate end of the argument list, you should also pass a 0 to fun.
fun(1,2,3,4,5,6,0);
fun(2,4,5,0);
First, end your list with 0, because you check for !=0 to detect the end. And also:
while((i=va_arg(k,int))!=0)
instead of
while(i=va_arg(k,int)!=0)
!= has higher precedence than =
This will give you the expected output:
1 2 3 4 5 6
Here's the complete code:
#include<stdio.h>
#include<stdarg.h>
void fun(int a,...)
{
va_list k;
va_start(k,a);
int i=0;
printf("%d ",a);
while((i=va_arg(k,int))!=0)
{
printf(" %d ",i);
}
va_end(k);
}
int main()
{
fun(1,2,3,4,5,6,0);
printf("\n");
//fun(2,4,5,0);
printf("\n");
//fun('c','f','g','l','\0');
getch();
return 0;
}