ReactOS Fundraising Campaign 2012
 
€ 4,410 / € 30,000

Information | Donate

Home | Info | Community | Development | myReactOS | Contact Us

  1. Home
  2. Community
  3. Development
  4. myReactOS
  5. Fundraiser 2012

  1. Main Page
  2. Alphabetical List
  3. Data Structures
  4. Directories
  5. File List
  6. Data Fields
  7. Globals
  8. Related Pages

ReactOS Development > Doxygen

pstcache.c
Go to the documentation of this file.
00001 /* -*- c-basic-offset: 8 -*-
00002    rdesktop: A Remote Desktop Protocol client.
00003    Persistent Bitmap Cache routines
00004    Copyright (C) Jeroen Meijer 2004-2005
00005 
00006    This program is free software; you can redistribute it and/or modify
00007    it under the terms of the GNU General Public License as published by
00008    the Free Software Foundation; either version 2 of the License, or
00009    (at your option) any later version.
00010 
00011    This program is distributed in the hope that it will be useful,
00012    but WITHOUT ANY WARRANTY; without even the implied warranty of
00013    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014    GNU General Public License for more details.
00015 
00016    You should have received a copy of the GNU General Public License along
00017    with this program; if not, write to the Free Software Foundation, Inc.,
00018    51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
00019 */
00020 
00021 #include <precomp.h>
00022 
00023 #define MAX_CELL_SIZE       0x1000  /* pixels */
00024 
00025 extern int g_server_depth;
00026 extern BOOL g_bitmap_cache;
00027 extern BOOL g_bitmap_cache_persist_enable;
00028 extern BOOL g_bitmap_cache_precache;
00029 
00030 int g_pstcache_fd[8];
00031 int g_pstcache_Bpp;
00032 BOOL g_pstcache_enumerated = False;
00033 uint8 zero_key[] = { 0, 0, 0, 0, 0, 0, 0, 0 };
00034 
00035 
00036 /* Update mru stamp/index for a bitmap */
00037 void
00038 pstcache_touch_bitmap(uint8 cache_id, uint16 cache_idx, uint32 stamp)
00039 {
00040     int fd;
00041 
00042     if (!IS_PERSISTENT(cache_id) || cache_idx >= BMPCACHE2_NUM_PSTCELLS)
00043         return;
00044 
00045     fd = g_pstcache_fd[cache_id];
00046     rd_lseek_file(fd, 12 + cache_idx * (g_pstcache_Bpp * MAX_CELL_SIZE + sizeof(CELLHEADER)));
00047     rd_write_file(fd, &stamp, sizeof(stamp));
00048 }
00049 
00050 /* Load a bitmap from the persistent cache */
00051 BOOL
00052 pstcache_load_bitmap(uint8 cache_id, uint16 cache_idx)
00053 {
00054     uint8 *celldata;
00055     int fd;
00056     CELLHEADER cellhdr;
00057     HBITMAP bitmap;
00058 
00059     if (!g_bitmap_cache_persist_enable)
00060         return False;
00061 
00062     if (!IS_PERSISTENT(cache_id) || cache_idx >= BMPCACHE2_NUM_PSTCELLS)
00063         return False;
00064 
00065     memset(&cellhdr, 0, sizeof(CELLHEADER));
00066 
00067     fd = g_pstcache_fd[cache_id];
00068     rd_lseek_file(fd, cache_idx * (g_pstcache_Bpp * MAX_CELL_SIZE + sizeof(CELLHEADER)));
00069     rd_read_file(fd, &cellhdr, sizeof(CELLHEADER));
00070     celldata = (uint8 *) xmalloc(cellhdr.length);
00071     rd_read_file(fd, celldata, cellhdr.length);
00072 
00073     bitmap = ui_create_bitmap(cellhdr.width, cellhdr.height, celldata);
00074     DEBUG(("Load bitmap from disk: id=%d, idx=%d, bmp=0x%x)\n", cache_id, cache_idx, bitmap));
00075     cache_put_bitmap(cache_id, cache_idx, bitmap);
00076 
00077     xfree(celldata);
00078     return True;
00079 }
00080 
00081 /* Store a bitmap in the persistent cache */
00082 BOOL
00083 pstcache_save_bitmap(uint8 cache_id, uint16 cache_idx, uint8 * key,
00084              uint8 width, uint8 height, uint16 length, uint8 * data)
00085 {
00086     int fd;
00087     CELLHEADER cellhdr;
00088 
00089     if (!IS_PERSISTENT(cache_id) || cache_idx >= BMPCACHE2_NUM_PSTCELLS)
00090         return False;
00091 
00092     memcpy(cellhdr.key, key, sizeof(HASH_KEY));
00093     cellhdr.width = width;
00094     cellhdr.height = height;
00095     cellhdr.length = length;
00096     cellhdr.stamp = 0;
00097 
00098     fd = g_pstcache_fd[cache_id];
00099     rd_lseek_file(fd, cache_idx * (g_pstcache_Bpp * MAX_CELL_SIZE + sizeof(CELLHEADER)));
00100     rd_write_file(fd, &cellhdr, sizeof(CELLHEADER));
00101     rd_write_file(fd, data, length);
00102 
00103     return True;
00104 }
00105 
00106 /* List the bitmap keys from the persistent cache file */
00107 int
00108 pstcache_enumerate(uint8 id, HASH_KEY * keylist)
00109 {
00110     int fd, n;
00111     uint16 idx;
00112     sint16 mru_idx[0xa00];
00113     uint32 mru_stamp[0xa00];
00114     CELLHEADER cellhdr;
00115 
00116     if (!(g_bitmap_cache && g_bitmap_cache_persist_enable && IS_PERSISTENT(id)))
00117         return 0;
00118 
00119     /* The server disconnects if the bitmap cache content is sent more than once */
00120     if (g_pstcache_enumerated)
00121         return 0;
00122 
00123     DEBUG_RDP5(("Persistent bitmap cache enumeration... "));
00124     for (idx = 0; idx < BMPCACHE2_NUM_PSTCELLS; idx++)
00125     {
00126         fd = g_pstcache_fd[id];
00127         rd_lseek_file(fd, idx * (g_pstcache_Bpp * MAX_CELL_SIZE + sizeof(CELLHEADER)));
00128         if (rd_read_file(fd, &cellhdr, sizeof(CELLHEADER)) <= 0)
00129             break;
00130 
00131         if (memcmp(cellhdr.key, zero_key, sizeof(HASH_KEY)) != 0)
00132         {
00133             memcpy(keylist[idx], cellhdr.key, sizeof(HASH_KEY));
00134 
00135             /* Pre-cache (not possible for 8 bit colour depth cause it needs a colourmap) */
00136             if (g_bitmap_cache_precache && cellhdr.stamp && g_server_depth > 8)
00137                 pstcache_load_bitmap(id, idx);
00138 
00139             /* Sort by stamp */
00140             for (n = idx; n > 0 && cellhdr.stamp < mru_stamp[n - 1]; n--)
00141             {
00142                 mru_idx[n] = mru_idx[n - 1];
00143                 mru_stamp[n] = mru_stamp[n - 1];
00144             }
00145 
00146             mru_idx[n] = idx;
00147             mru_stamp[n] = cellhdr.stamp;
00148         }
00149         else
00150         {
00151             break;
00152         }
00153     }
00154 
00155     DEBUG_RDP5(("%d cached bitmaps.\n", idx));
00156 
00157     cache_rebuild_bmpcache_linked_list(id, mru_idx, idx);
00158     g_pstcache_enumerated = True;
00159     return idx;
00160 }
00161 
00162 /* initialise the persistent bitmap cache */
00163 BOOL
00164 pstcache_init(uint8 cache_id)
00165 {
00166     int fd;
00167     char filename[256];
00168 
00169     if (g_pstcache_enumerated)
00170         return True;
00171 
00172     g_pstcache_fd[cache_id] = 0;
00173 
00174     if (!(g_bitmap_cache && g_bitmap_cache_persist_enable))
00175         return False;
00176 
00177     if (!rd_pstcache_mkdir())
00178     {
00179         DEBUG(("failed to get/make cache directory!\n"));
00180         return False;
00181     }
00182 
00183     g_pstcache_Bpp = (g_server_depth + 7) / 8;
00184     sprintf(filename, "cache/pstcache_%d_%d", cache_id, g_pstcache_Bpp);
00185     DEBUG(("persistent bitmap cache file: %s\n", filename));
00186 
00187     fd = rd_open_file(filename);
00188     if (fd == -1)
00189         return False;
00190 
00191     if (!rd_lock_file(fd, 0, 0))
00192     {
00193         warning("Persistent bitmap caching is disabled. (The file is already in use)\n");
00194         rd_close_file(fd);
00195         return False;
00196     }
00197 
00198     g_pstcache_fd[cache_id] = fd;
00199     return True;
00200 }

Generated on Sun May 27 2012 04:17:10 for ReactOS by doxygen 1.7.6.1

ReactOS is a registered trademark or a trademark of ReactOS Foundation in the United States and other countries.