C Function Fgetpos
# C Library Function - fgetpos()
The `fgetpos()` function is a standard C library function defined in the `` header. It is used to retrieve the current file position indicator of a stream and store it in a platform-independent object.
Unlike `ftell()`, which returns a simple `long` integer representing the byte offset, `fgetpos()` is designed to handle very large files and complex multibyte encoding states by using a dedicated type called `fpos_t`.
---
## Syntax
```c
int fgetpos(FILE *stream, fpos_t *pos);
```
### Parameters
* **`stream`**: A pointer to a `FILE` object that identifies the input/output stream.
* **`pos`**: A pointer to an `fpos_t` object where the current position information will be stored.
### Return Value
* **`0`**: On success, the function returns zero.
* **Non-zero value**: On failure, the function returns a non-zero value and sets the global variable `errno` to a positive value representing the specific error.
---
## Understanding `fpos_t`
The `fpos_t` type is a non-array object type capable of uniquely specifying the position of every byte within a file. Depending on the compiler and platform, `fpos_t` can be a simple integer type (like `long long`), or a complex structure containing both a file offset and state information for wide-character/multibyte encodings.
Because its implementation is platform-dependent, you should not attempt to read, modify, or print the contents of an `fpos_t` variable directly. Instead, it should only be populated by `fgetpos()` and consumed by `fsetpos()`.
---
## Code Examples
### Example 1: Saving and Restoring File Position
The following example demonstrates how to use `fgetpos()` to save the initial position of a file stream, write some text, and then use `fsetpos()` to return to the saved position and overwrite the content.
```c
#include
int main()
{
FILE *fp;
fpos_t position;
// Open file for reading and writing
fp = fopen("file.txt", "w+");
if (fp == NULL) {
perror("Error opening file");
return -1;
}
// Store the initial position (beginning of the file)
if (fgetpos(fp, &position) != 0) {
perror("Error getting file position");
fclose(fp);
return -1;
}
// Write initial content
fputs("Hello, World!", fp);
// Restore the position back to the beginning of the file
if (fsetpos(fp, &position) != 0) {
perror("Error setting file position");
fclose(fp);
return -1;
}
// Overwrite the initial content
fputs("This overwrites the previous content", fp);
fclose(fp);
return 0;
}
```
#### Output
When you run the program above, it creates a file named `file.txt` with the following content:
```text
This overwrites the previous content
```
---
### Example 2: Reading and Verifying File Content
You can verify the contents of the generated `file.txt` using the following program:
```c
#include
int main()
{
FILE *fp;
int c;
// Open the file in read-only mode
fp = fopen("file.txt", "r");
if (fp == NULL) {
perror("Error opening file");
return -1;
}
// Read and print character by character until EOF
while (1)
{
c = fgetc(fp);
if (feof(fp))
{
break;
}
printf("%c", c);
}
fclose(fp);
return 0;
}
```
---
## Key Considerations
### `fgetpos()` vs. `ftell()`
* **File Size Limits**: `ftell()` returns a `long` integer, which is typically limited to 2GB or 4GB on many 32-bit systems. `fgetpos()` uses `fpos_t`, which is designed to support files larger than 4GB (LFS - Large File Support).
* **Multibyte Streams**: For wide-character streams (`wchar.h`), `fgetpos()` stores the state information required to correctly parse multibyte characters, whereas `ftell()` only tracks byte offsets.
### Best Practices
* **Error Checking**: Always check the return value of `fgetpos()`. If it returns a non-zero value, the position was not successfully recorded, and passing that `fpos_t` variable to `fsetpos()` will result in undefined behavior.
* **Portability**: Do not perform arithmetic operations (like `position + 10`) on `fpos_t` variables, as they are not guaranteed to be numeric types across different operating systems.
YouTip