root/src/vfs/sftpfs/vfs_class.c

/* [previous][next][first][last][top][bottom][index][help]  */

DEFINITIONS

This source file includes following definitions.
  1. sftpfs_cb_init
  2. sftpfs_cb_done
  3. sftpfs_cb_open
  4. sftpfs_cb_opendir
  5. sftpfs_cb_readdir
  6. sftpfs_cb_closedir
  7. sftpfs_cb_lstat
  8. sftpfs_cb_stat
  9. sftpfs_cb_fstat
  10. sftpfs_cb_readlink
  11. sftpfs_cb_utime
  12. sftpfs_cb_symlink
  13. sftpfs_cb_mknod
  14. sftpfs_cb_link
  15. sftpfs_cb_chown
  16. sftpfs_cb_read
  17. sftpfs_cb_write
  18. sftpfs_cb_close
  19. sftpfs_cb_chmod
  20. sftpfs_cb_mkdir
  21. sftpfs_cb_rmdir
  22. sftpfs_cb_lseek
  23. sftpfs_cb_unlink
  24. sftpfs_cb_rename
  25. sftpfs_cb_errno
  26. sftpfs_cb_fill_names
  27. sftpfs_init_class

   1 /* Virtual File System: SFTP file system.
   2    The VFS class functions
   3 
   4    Copyright (C) 2011-2019
   5    Free Software Foundation, Inc.
   6 
   7    Written by:
   8    Ilia Maslakov <il.smind@gmail.com>, 2011
   9    Slava Zanko <slavazanko@gmail.com>, 2011, 2012
  10 
  11    This file is part of the Midnight Commander.
  12 
  13    The Midnight Commander is free software: you can redistribute it
  14    and/or modify it under the terms of the GNU General Public License as
  15    published by the Free Software Foundation, either version 3 of the License,
  16    or (at your option) any later version.
  17 
  18    The Midnight Commander is distributed in the hope that it will be useful,
  19    but WITHOUT ANY WARRANTY; without even the implied warranty of
  20    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  21    GNU General Public License for more details.
  22 
  23    You should have received a copy of the GNU General Public License
  24    along with this program.  If not, see <http://www.gnu.org/licenses/>.
  25  */
  26 
  27 #include <config.h>
  28 #include <errno.h>
  29 
  30 #include "lib/global.h"
  31 #include "lib/widget.h"
  32 #include "lib/vfs/gc.h"
  33 #include "lib/tty/tty.h"        /* tty_enable_interrupt_key () */
  34 
  35 #include "internal.h"
  36 
  37 /*** global variables ****************************************************************************/
  38 
  39 /*** file scope macro definitions ****************************************************************/
  40 
  41 /*** file scope type declarations ****************************************************************/
  42 
  43 /*** file scope variables ************************************************************************/
  44 
  45 /*** file scope functions ************************************************************************/
  46 /* --------------------------------------------------------------------------------------------- */
  47 /**
  48  * Callback for VFS-class init action.
  49  *
  50  * @param me structure of VFS class
  51  */
  52 
  53 static int
  54 sftpfs_cb_init (struct vfs_class *me)
     /* [previous][next][first][last][top][bottom][index][help]  */
  55 {
  56     (void) me;
  57 
  58     if (libssh2_init (0) != 0)
  59         return 0;
  60 
  61     sftpfs_filename_buffer = g_string_new ("");
  62     sftpfs_init_config_variables_patterns ();
  63     return 1;
  64 }
  65 
  66 /* --------------------------------------------------------------------------------------------- */
  67 /**
  68  * Callback for VFS-class deinit action.
  69  *
  70  * @param me structure of VFS class
  71  */
  72 
  73 static void
  74 sftpfs_cb_done (struct vfs_class *me)
     /* [previous][next][first][last][top][bottom][index][help]  */
  75 {
  76     (void) me;
  77 
  78     sftpfs_deinit_config_variables_patterns ();
  79     g_string_free (sftpfs_filename_buffer, TRUE);
  80     libssh2_exit ();
  81 }
  82 
  83 /* --------------------------------------------------------------------------------------------- */
  84 /**
  85  * Callback for opening file.
  86  *
  87  * @param vpath path to file
  88  * @param flags flags (see man 2 open)
  89  * @param mode  mode (see man 2 open)
  90  * @return file data handler if success, NULL otherwise
  91  */
  92 
  93 static void *
  94 sftpfs_cb_open (const vfs_path_t * vpath, int flags, mode_t mode)
     /* [previous][next][first][last][top][bottom][index][help]  */
  95 {
  96     vfs_file_handler_t *fh;
  97     const vfs_path_element_t *path_element;
  98     struct vfs_s_super *super;
  99     const char *path_super;
 100     struct vfs_s_inode *path_inode;
 101     GError *mcerror = NULL;
 102     gboolean is_changed = FALSE;
 103 
 104     path_element = vfs_path_get_by_index (vpath, -1);
 105 
 106     path_super = vfs_s_get_path (vpath, &super, 0);
 107     if (path_super == NULL)
 108         return NULL;
 109 
 110     path_inode = vfs_s_find_inode (path_element->class, super, path_super, LINK_FOLLOW, FL_NONE);
 111     if (path_inode != NULL && ((flags & (O_CREAT | O_EXCL)) == (O_CREAT | O_EXCL)))
 112     {
 113         path_element->class->verrno = EEXIST;
 114         return NULL;
 115     }
 116 
 117     if (path_inode == NULL)
 118     {
 119         char *dirname, *name;
 120         struct vfs_s_entry *ent;
 121         struct vfs_s_inode *dir;
 122 
 123         dirname = g_path_get_dirname (path_super);
 124         name = g_path_get_basename (path_super);
 125         dir = vfs_s_find_inode (path_element->class, super, dirname, LINK_FOLLOW, FL_DIR);
 126         if (dir == NULL)
 127         {
 128             g_free (dirname);
 129             g_free (name);
 130             return NULL;
 131         }
 132         ent = vfs_s_generate_entry (path_element->class, name, dir, 0755);
 133         path_inode = ent->ino;
 134         vfs_s_insert_entry (path_element->class, dir, ent);
 135         g_free (dirname);
 136         g_free (name);
 137         is_changed = TRUE;
 138     }
 139 
 140     if (S_ISDIR (path_inode->st.st_mode))
 141     {
 142         path_element->class->verrno = EISDIR;
 143         return NULL;
 144     }
 145 
 146     fh = sftpfs_fh_new (path_inode, is_changed);
 147 
 148     if (!sftpfs_open_file (fh, flags, mode, &mcerror))
 149     {
 150         mc_error_message (&mcerror, NULL);
 151         g_free (fh);
 152         return NULL;
 153     }
 154 
 155     vfs_rmstamp (path_element->class, (vfsid) super);
 156     super->fd_usage++;
 157     fh->ino->st.st_nlink++;
 158     return fh;
 159 }
 160 
 161 /* --------------------------------------------------------------------------------------------- */
 162 /**
 163  * Callback for opening directory.
 164  *
 165  * @param vpath path to directory
 166  * @return directory data handler if success, NULL otherwise
 167  */
 168 
 169 static void *
 170 sftpfs_cb_opendir (const vfs_path_t * vpath)
     /* [previous][next][first][last][top][bottom][index][help]  */
 171 {
 172     GError *mcerror = NULL;
 173     void *ret_value;
 174 
 175     /* reset interrupt flag */
 176     tty_got_interrupt ();
 177 
 178     ret_value = sftpfs_opendir (vpath, &mcerror);
 179     mc_error_message (&mcerror, NULL);
 180     return ret_value;
 181 }
 182 
 183 /* --------------------------------------------------------------------------------------------- */
 184 /**
 185  * Callback for reading directory entry.
 186  *
 187  * @param data directory data handler
 188  * @return information about direntry if success, NULL otherwise
 189  */
 190 
 191 static void *
 192 sftpfs_cb_readdir (void *data)
     /* [previous][next][first][last][top][bottom][index][help]  */
 193 {
 194     GError *mcerror = NULL;
 195     union vfs_dirent *sftpfs_dirent;
 196 
 197     if (tty_got_interrupt ())
 198     {
 199         tty_disable_interrupt_key ();
 200         return NULL;
 201     }
 202 
 203     sftpfs_dirent = sftpfs_readdir (data, &mcerror);
 204     if (!mc_error_message (&mcerror, NULL))
 205     {
 206         if (sftpfs_dirent != NULL)
 207             vfs_print_message (_("sftp: (Ctrl-G break) Listing... %s"), sftpfs_dirent->dent.d_name);
 208         else
 209             vfs_print_message ("%s", _("sftp: Listing done."));
 210     }
 211 
 212     return sftpfs_dirent;
 213 }
 214 
 215 /* --------------------------------------------------------------------------------------------- */
 216 /**
 217  * Callback for closing directory.
 218  *
 219  * @param data directory data handler
 220  * @return 0 if success, negative value otherwise
 221  */
 222 
 223 static int
 224 sftpfs_cb_closedir (void *data)
     /* [previous][next][first][last][top][bottom][index][help]  */
 225 {
 226     int rc;
 227     GError *mcerror = NULL;
 228 
 229     rc = sftpfs_closedir (data, &mcerror);
 230     mc_error_message (&mcerror, NULL);
 231     return rc;
 232 }
 233 
 234 /* --------------------------------------------------------------------------------------------- */
 235 /**
 236  * Callback for lstat VFS-function.
 237  *
 238  * @param vpath path to file or directory
 239  * @param buf   buffer for store stat-info
 240  * @return 0 if success, negative value otherwise
 241  */
 242 
 243 static int
 244 sftpfs_cb_lstat (const vfs_path_t * vpath, struct stat *buf)
     /* [previous][next][first][last][top][bottom][index][help]  */
 245 {
 246     int rc;
 247     GError *mcerror = NULL;
 248 
 249     rc = sftpfs_lstat (vpath, buf, &mcerror);
 250     mc_error_message (&mcerror, NULL);
 251     return rc;
 252 }
 253 
 254 /* --------------------------------------------------------------------------------------------- */
 255 /**
 256  * Callback for stat VFS-function.
 257  *
 258  * @param vpath path to file or directory
 259  * @param buf   buffer for store stat-info
 260  * @return 0 if success, negative value otherwise
 261  */
 262 
 263 static int
 264 sftpfs_cb_stat (const vfs_path_t * vpath, struct stat *buf)
     /* [previous][next][first][last][top][bottom][index][help]  */
 265 {
 266     int rc;
 267     GError *mcerror = NULL;
 268 
 269     rc = sftpfs_stat (vpath, buf, &mcerror);
 270     mc_error_message (&mcerror, NULL);
 271     return rc;
 272 }
 273 
 274 /* --------------------------------------------------------------------------------------------- */
 275 /**
 276  * Callback for fstat VFS-function.
 277  *
 278  * @param data file data handler
 279  * @param buf  buffer for store stat-info
 280  * @return 0 if success, negative value otherwise
 281  */
 282 
 283 static int
 284 sftpfs_cb_fstat (void *data, struct stat *buf)
     /* [previous][next][first][last][top][bottom][index][help]  */
 285 {
 286     int rc;
 287     GError *mcerror = NULL;
 288 
 289     rc = sftpfs_fstat (data, buf, &mcerror);
 290     mc_error_message (&mcerror, NULL);
 291     return rc;
 292 }
 293 
 294 /* --------------------------------------------------------------------------------------------- */
 295 /**
 296  * Callback for readlink VFS-function.
 297  *
 298  * @param vpath path to file or directory
 299  * @param buf   buffer for store stat-info
 300  * @param size  buffer size
 301  * @return 0 if success, negative value otherwise
 302  */
 303 
 304 static int
 305 sftpfs_cb_readlink (const vfs_path_t * vpath, char *buf, size_t size)
     /* [previous][next][first][last][top][bottom][index][help]  */
 306 {
 307     int rc;
 308     GError *mcerror = NULL;
 309 
 310     rc = sftpfs_readlink (vpath, buf, size, &mcerror);
 311     mc_error_message (&mcerror, NULL);
 312     return rc;
 313 }
 314 
 315 /* --------------------------------------------------------------------------------------------- */
 316 /**
 317  * Callback for utime VFS-function.
 318  *
 319  * @param vpath path to file or directory
 320  * @param times access and modification time to set
 321  * @return 0 if success, negative value otherwise
 322  */
 323 
 324 static int
 325 sftpfs_cb_utime (const vfs_path_t * vpath, mc_timesbuf_t * times)
     /* [previous][next][first][last][top][bottom][index][help]  */
 326 {
 327     int rc;
 328     GError *mcerror = NULL;
 329 #ifdef HAVE_UTIMENSAT
 330     time_t atime = (*times)[0].tv_sec;
 331     time_t mtime = (*times)[1].tv_sec;
 332 #else
 333     time_t atime = times->actime;
 334     time_t mtime = times->modtime;
 335 #endif
 336 
 337     rc = sftpfs_utime (vpath, atime, mtime, &mcerror);
 338     mc_error_message (&mcerror, NULL);
 339     return rc;
 340 }
 341 
 342 /* --------------------------------------------------------------------------------------------- */
 343 /**
 344  * Callback for symlink VFS-function.
 345  *
 346  * @param vpath1 path to file or directory
 347  * @param vpath2 path to symlink
 348  * @return 0 if success, negative value otherwise
 349  */
 350 
 351 static int
 352 sftpfs_cb_symlink (const vfs_path_t * vpath1, const vfs_path_t * vpath2)
     /* [previous][next][first][last][top][bottom][index][help]  */
 353 {
 354     int rc;
 355     GError *mcerror = NULL;
 356 
 357     rc = sftpfs_symlink (vpath1, vpath2, &mcerror);
 358     mc_error_message (&mcerror, NULL);
 359     return rc;
 360 }
 361 
 362 /* --------------------------------------------------------------------------------------------- */
 363 /**
 364  * Callback for symlink VFS-function.
 365  *
 366  * @param vpath unused
 367  * @param mode  unused
 368  * @param dev   unused
 369  * @return always 0
 370  */
 371 
 372 static int
 373 sftpfs_cb_mknod (const vfs_path_t * vpath, mode_t mode, dev_t dev)
     /* [previous][next][first][last][top][bottom][index][help]  */
 374 {
 375     (void) vpath;
 376     (void) mode;
 377     (void) dev;
 378 
 379     return 0;
 380 }
 381 
 382 /* --------------------------------------------------------------------------------------------- */
 383 /**
 384  * Callback for link VFS-function.
 385  *
 386  * @param vpath1 unused
 387  * @param vpath2 unused
 388  * @return always 0
 389  */
 390 
 391 static int
 392 sftpfs_cb_link (const vfs_path_t * vpath1, const vfs_path_t * vpath2)
     /* [previous][next][first][last][top][bottom][index][help]  */
 393 {
 394     (void) vpath1;
 395     (void) vpath2;
 396 
 397     return 0;
 398 }
 399 
 400 /* --------------------------------------------------------------------------------------------- */
 401 /**
 402  * Callback for chown VFS-function.
 403  *
 404  * @param vpath unused
 405  * @param owner unused
 406  * @param group unused
 407  * @return always 0
 408  */
 409 
 410 static int
 411 sftpfs_cb_chown (const vfs_path_t * vpath, uid_t owner, gid_t group)
     /* [previous][next][first][last][top][bottom][index][help]  */
 412 {
 413     (void) vpath;
 414     (void) owner;
 415     (void) group;
 416 
 417     return 0;
 418 }
 419 
 420 /* --------------------------------------------------------------------------------------------- */
 421 /**
 422  * Callback for reading file content.
 423  *
 424  * @param data   file data handler
 425  * @param buffer buffer for data
 426  * @param count  data size
 427  * @return 0 if success, negative value otherwise
 428  */
 429 
 430 static ssize_t
 431 sftpfs_cb_read (void *data, char *buffer, size_t count)
     /* [previous][next][first][last][top][bottom][index][help]  */
 432 {
 433     int rc;
 434     GError *mcerror = NULL;
 435     vfs_file_handler_t *fh = VFS_FILE_HANDLER (data);
 436 
 437     if (tty_got_interrupt ())
 438     {
 439         tty_disable_interrupt_key ();
 440         return 0;
 441     }
 442 
 443     rc = sftpfs_read_file (fh, buffer, count, &mcerror);
 444     mc_error_message (&mcerror, NULL);
 445     return rc;
 446 }
 447 
 448 /* --------------------------------------------------------------------------------------------- */
 449 /**
 450  * Callback for writing file content.
 451  *
 452  * @param data  file data handler
 453  * @param buf   buffer for data
 454  * @param count data size
 455  * @return 0 if success, negative value otherwise
 456  */
 457 
 458 static ssize_t
 459 sftpfs_cb_write (void *data, const char *buf, size_t nbyte)
     /* [previous][next][first][last][top][bottom][index][help]  */
 460 {
 461     int rc;
 462     GError *mcerror = NULL;
 463     vfs_file_handler_t *fh = VFS_FILE_HANDLER (data);
 464 
 465     rc = sftpfs_write_file (fh, buf, nbyte, &mcerror);
 466     mc_error_message (&mcerror, NULL);
 467     return rc;
 468 }
 469 
 470 /* --------------------------------------------------------------------------------------------- */
 471 /**
 472  * Callback for close file.
 473  *
 474  * @param data file data handler
 475  * @return 0 if success, negative value otherwise
 476  */
 477 
 478 static int
 479 sftpfs_cb_close (void *data)
     /* [previous][next][first][last][top][bottom][index][help]  */
 480 {
 481     int rc;
 482     GError *mcerror = NULL;
 483     struct vfs_s_super *super = VFS_FILE_HANDLER_SUPER (data);
 484     vfs_file_handler_t *fh = VFS_FILE_HANDLER (data);
 485 
 486     super->fd_usage--;
 487     if (super->fd_usage == 0)
 488         vfs_stamp_create (sftpfs_class, super);
 489 
 490     rc = sftpfs_close_file (fh, &mcerror);
 491     mc_error_message (&mcerror, NULL);
 492 
 493     if (fh->handle != -1)
 494         close (fh->handle);
 495 
 496     vfs_s_free_inode (sftpfs_class, fh->ino);
 497 
 498     return rc;
 499 }
 500 
 501 /* --------------------------------------------------------------------------------------------- */
 502 /**
 503  * Callback for chmod VFS-function.
 504  *
 505  * @param vpath path to file or directory
 506  * @param mode  mode (see man 2 open)
 507  * @return 0 if success, negative value otherwise
 508  */
 509 
 510 static int
 511 sftpfs_cb_chmod (const vfs_path_t * vpath, mode_t mode)
     /* [previous][next][first][last][top][bottom][index][help]  */
 512 {
 513     int rc;
 514     GError *mcerror = NULL;
 515 
 516     rc = sftpfs_chmod (vpath, mode, &mcerror);
 517     mc_error_message (&mcerror, NULL);
 518     return rc;
 519 }
 520 
 521 /* --------------------------------------------------------------------------------------------- */
 522 /**
 523  * Callback for mkdir VFS-function.
 524  *
 525  * @param vpath path directory
 526  * @param mode  mode (see man 2 open)
 527  * @return 0 if success, negative value otherwise
 528  */
 529 
 530 static int
 531 sftpfs_cb_mkdir (const vfs_path_t * vpath, mode_t mode)
     /* [previous][next][first][last][top][bottom][index][help]  */
 532 {
 533     int rc;
 534     GError *mcerror = NULL;
 535 
 536     rc = sftpfs_mkdir (vpath, mode, &mcerror);
 537     mc_error_message (&mcerror, NULL);
 538     return rc;
 539 }
 540 
 541 /* --------------------------------------------------------------------------------------------- */
 542 /**
 543  * Callback for rmdir VFS-function.
 544  *
 545  * @param vpath path directory
 546  * @return 0 if success, negative value otherwise
 547  */
 548 
 549 static int
 550 sftpfs_cb_rmdir (const vfs_path_t * vpath)
     /* [previous][next][first][last][top][bottom][index][help]  */
 551 {
 552     int rc;
 553     GError *mcerror = NULL;
 554 
 555     rc = sftpfs_rmdir (vpath, &mcerror);
 556     mc_error_message (&mcerror, NULL);
 557     return rc;
 558 }
 559 
 560 /* --------------------------------------------------------------------------------------------- */
 561 /**
 562  * Callback for lseek VFS-function.
 563  *
 564  * @param data   file data handler
 565  * @param offset file offset
 566  * @param whence method of seek (at begin, at current, at end)
 567  * @return 0 if success, negative value otherwise
 568  */
 569 
 570 static off_t
 571 sftpfs_cb_lseek (void *data, off_t offset, int whence)
     /* [previous][next][first][last][top][bottom][index][help]  */
 572 {
 573     off_t ret_offset;
 574     vfs_file_handler_t *fh = VFS_FILE_HANDLER (data);
 575     GError *mcerror = NULL;
 576 
 577     ret_offset = sftpfs_lseek (fh, offset, whence, &mcerror);
 578     mc_error_message (&mcerror, NULL);
 579     return ret_offset;
 580 }
 581 
 582 /* --------------------------------------------------------------------------------------------- */
 583 /**
 584  * Callback for unlink VFS-function.
 585  *
 586  * @param vpath path to file or directory
 587  * @return 0 if success, negative value otherwise
 588  */
 589 
 590 static int
 591 sftpfs_cb_unlink (const vfs_path_t * vpath)
     /* [previous][next][first][last][top][bottom][index][help]  */
 592 {
 593     int rc;
 594     GError *mcerror = NULL;
 595 
 596     rc = sftpfs_unlink (vpath, &mcerror);
 597     mc_error_message (&mcerror, NULL);
 598     return rc;
 599 }
 600 
 601 /* --------------------------------------------------------------------------------------------- */
 602 /**
 603  * Callback for rename VFS-function.
 604  *
 605  * @param vpath1 path to source file or directory
 606  * @param vpath2 path to destination file or directory
 607  * @return 0 if success, negative value otherwise
 608  */
 609 
 610 static int
 611 sftpfs_cb_rename (const vfs_path_t * vpath1, const vfs_path_t * vpath2)
     /* [previous][next][first][last][top][bottom][index][help]  */
 612 {
 613     int rc;
 614     GError *mcerror = NULL;
 615 
 616     rc = sftpfs_rename (vpath1, vpath2, &mcerror);
 617     mc_error_message (&mcerror, NULL);
 618     return rc;
 619 }
 620 
 621 /* --------------------------------------------------------------------------------------------- */
 622 /**
 623  * Callback for errno VFS-function.
 624  *
 625  * @param me unused
 626  * @return value of errno global variable
 627  */
 628 
 629 static int
 630 sftpfs_cb_errno (struct vfs_class *me)
     /* [previous][next][first][last][top][bottom][index][help]  */
 631 {
 632     (void) me;
 633     return errno;
 634 }
 635 
 636 /* --------------------------------------------------------------------------------------------- */
 637 /**
 638  * Callback for fill_names VFS function.
 639  * Add SFTP connections to the 'Active VFS connections'  list
 640  *
 641  * @param me   unused
 642  * @param func callback function for adding SFTP-connection to list of active connections
 643  */
 644 
 645 static void
 646 sftpfs_cb_fill_names (struct vfs_class *me, fill_names_f func)
     /* [previous][next][first][last][top][bottom][index][help]  */
 647 {
 648     GList *iter;
 649 
 650     (void) me;
 651 
 652     for (iter = sftpfs_subclass.supers; iter != NULL; iter = g_list_next (iter))
 653     {
 654         const struct vfs_s_super *super = (const struct vfs_s_super *) iter->data;
 655         char *name;
 656 
 657         name = vfs_path_element_build_pretty_path_str (super->path_element);
 658 
 659         func (name);
 660         g_free (name);
 661     }
 662 }
 663 
 664 /* --------------------------------------------------------------------------------------------- */
 665 /*** public functions ****************************************************************************/
 666 /* --------------------------------------------------------------------------------------------- */
 667 /**
 668  * Initialization of VFS class structure.
 669  *
 670  * @return the VFS class structure.
 671  */
 672 
 673 void
 674 sftpfs_init_class (void)
     /* [previous][next][first][last][top][bottom][index][help]  */
 675 {
 676     sftpfs_class->init = sftpfs_cb_init;
 677     sftpfs_class->done = sftpfs_cb_done;
 678 
 679     sftpfs_class->fill_names = sftpfs_cb_fill_names;
 680 
 681     sftpfs_class->opendir = sftpfs_cb_opendir;
 682     sftpfs_class->readdir = sftpfs_cb_readdir;
 683     sftpfs_class->closedir = sftpfs_cb_closedir;
 684     sftpfs_class->mkdir = sftpfs_cb_mkdir;
 685     sftpfs_class->rmdir = sftpfs_cb_rmdir;
 686 
 687     sftpfs_class->stat = sftpfs_cb_stat;
 688     sftpfs_class->lstat = sftpfs_cb_lstat;
 689     sftpfs_class->fstat = sftpfs_cb_fstat;
 690     sftpfs_class->readlink = sftpfs_cb_readlink;
 691     sftpfs_class->symlink = sftpfs_cb_symlink;
 692     sftpfs_class->link = sftpfs_cb_link;
 693     sftpfs_class->utime = sftpfs_cb_utime;
 694     sftpfs_class->mknod = sftpfs_cb_mknod;
 695     sftpfs_class->chown = sftpfs_cb_chown;
 696     sftpfs_class->chmod = sftpfs_cb_chmod;
 697 
 698     sftpfs_class->open = sftpfs_cb_open;
 699     sftpfs_class->read = sftpfs_cb_read;
 700     sftpfs_class->write = sftpfs_cb_write;
 701     sftpfs_class->close = sftpfs_cb_close;
 702     sftpfs_class->lseek = sftpfs_cb_lseek;
 703     sftpfs_class->unlink = sftpfs_cb_unlink;
 704     sftpfs_class->rename = sftpfs_cb_rename;
 705     sftpfs_class->ferrno = sftpfs_cb_errno;
 706 }
 707 
 708 /* --------------------------------------------------------------------------------------------- */

/* [previous][next][first][last][top][bottom][index][help]  */